@@ -60,7 +60,7 @@ import javax.inject.Inject
60
60
@ContributesBinding(AppScope ::class )
61
61
@SingleIn(AppScope ::class )
62
62
class RustMatrixAuthenticationService @Inject constructor(
63
- baseDirectory : File ,
63
+ private val baseDirectory : File ,
64
64
private val coroutineDispatchers : CoroutineDispatchers ,
65
65
private val sessionStore : SessionStore ,
66
66
private val rustMatrixClientFactory : RustMatrixClientFactory ,
@@ -70,10 +70,18 @@ class RustMatrixAuthenticationService @Inject constructor(
70
70
// Passphrase which will be used for new sessions. Existing sessions will use the passphrase
71
71
// stored in the SessionData.
72
72
private val pendingPassphrase = getDatabasePassphrase()
73
- private val sessionPath = File (baseDirectory, UUID .randomUUID().toString()).absolutePath
73
+ // Need to keep a copy of the current session path to delete it.
74
+ // Ideally it would be possible to get the sessionPath from the Client to avoid doing this.
75
+ private var sessionPath: File ? = null
74
76
private var currentClient: Client ? = null
75
77
private var currentHomeserver = MutableStateFlow <MatrixHomeServerDetails ?>(null )
76
78
79
+ private fun rotateSessionPath (): File {
80
+ sessionPath?.deleteRecursively()
81
+ return File (baseDirectory, UUID .randomUUID().toString())
82
+ .also { sessionPath = it }
83
+ }
84
+
77
85
override fun loggedInStateFlow (): Flow <LoggedInState > {
78
86
return sessionStore.isLoggedIn()
79
87
}
@@ -117,8 +125,9 @@ class RustMatrixAuthenticationService @Inject constructor(
117
125
118
126
override suspend fun setHomeserver (homeserver : String ): Result <Unit > =
119
127
withContext(coroutineDispatchers.io) {
128
+ val emptySessionPath = rotateSessionPath()
120
129
runCatching {
121
- val client = getBaseClientBuilder()
130
+ val client = getBaseClientBuilder(emptySessionPath )
122
131
.serverNameOrHomeserverUrl(homeserver)
123
132
.build()
124
133
currentClient = client
@@ -135,13 +144,14 @@ class RustMatrixAuthenticationService @Inject constructor(
135
144
withContext(coroutineDispatchers.io) {
136
145
runCatching {
137
146
val client = currentClient ? : error(" You need to call `setHomeserver()` first" )
147
+ val currentSessionPath = sessionPath ? : error(" You need to call `setHomeserver()` first" )
138
148
client.login(username, password, " Element X Android" , null )
139
149
val sessionData = client.session()
140
150
.toSessionData(
141
151
isTokenValid = true ,
142
152
loginType = LoginType .PASSWORD ,
143
153
passphrase = pendingPassphrase,
144
- sessionPath = sessionPath ,
154
+ sessionPath = currentSessionPath.absolutePath ,
145
155
)
146
156
clear()
147
157
sessionStore.storeData(sessionData)
@@ -185,13 +195,14 @@ class RustMatrixAuthenticationService @Inject constructor(
185
195
return withContext(coroutineDispatchers.io) {
186
196
runCatching {
187
197
val client = currentClient ? : error(" You need to call `setHomeserver()` first" )
198
+ val currentSessionPath = sessionPath ? : error(" You need to call `setHomeserver()` first" )
188
199
val urlForOidcLogin = pendingOidcAuthorizationData ? : error(" You need to call `getOidcUrl()` first" )
189
200
client.loginWithOidcCallback(urlForOidcLogin, callbackUrl)
190
201
val sessionData = client.session().toSessionData(
191
202
isTokenValid = true ,
192
203
loginType = LoginType .OIDC ,
193
204
passphrase = pendingPassphrase,
194
- sessionPath = sessionPath ,
205
+ sessionPath = currentSessionPath.absolutePath ,
195
206
)
196
207
clear()
197
208
pendingOidcAuthorizationData?.close()
@@ -206,9 +217,10 @@ class RustMatrixAuthenticationService @Inject constructor(
206
217
207
218
override suspend fun loginWithQrCode (qrCodeData : MatrixQrCodeLoginData , progress : (QrCodeLoginStep ) -> Unit ) =
208
219
withContext(coroutineDispatchers.io) {
220
+ val emptySessionPath = rotateSessionPath()
209
221
runCatching {
210
222
val client = rustMatrixClientFactory.getBaseClientBuilder(
211
- sessionPath = sessionPath ,
223
+ sessionPath = emptySessionPath.absolutePath ,
212
224
passphrase = pendingPassphrase,
213
225
slidingSyncProxy = AuthenticationConfig .SLIDING_SYNC_PROXY_URL ,
214
226
slidingSync = ClientBuilderSlidingSync .Discovered ,
@@ -229,7 +241,7 @@ class RustMatrixAuthenticationService @Inject constructor(
229
241
isTokenValid = true ,
230
242
loginType = LoginType .QR ,
231
243
passphrase = pendingPassphrase,
232
- sessionPath = sessionPath ,
244
+ sessionPath = emptySessionPath.absolutePath ,
233
245
)
234
246
sessionStore.storeData(sessionData)
235
247
SessionId (sessionData.userId)
@@ -246,11 +258,13 @@ class RustMatrixAuthenticationService @Inject constructor(
246
258
}
247
259
Timber .e(throwable, " Failed to login with QR code" )
248
260
}
249
- }
261
+ }
250
262
251
- private fun getBaseClientBuilder () = rustMatrixClientFactory
263
+ private fun getBaseClientBuilder (
264
+ sessionPath : File ,
265
+ ) = rustMatrixClientFactory
252
266
.getBaseClientBuilder(
253
- sessionPath = sessionPath,
267
+ sessionPath = sessionPath.absolutePath ,
254
268
passphrase = pendingPassphrase,
255
269
slidingSyncProxy = AuthenticationConfig .SLIDING_SYNC_PROXY_URL ,
256
270
slidingSync = ClientBuilderSlidingSync .Discovered ,
0 commit comments