From 38d81d60933b46085ad5458b0fad6e62eaf92815 Mon Sep 17 00:00:00 2001 From: Christian Pauly Date: Thu, 17 Jun 2021 12:37:10 +0200 Subject: [PATCH] fix: Migrate missing device keys Currently we only migrate the client and SSSSCache but this leads to the problem that we are no longer self signed after the migration. We need to migrate all device keys too. This also abstracts the migration code in a method. init() is too large already... --- lib/src/client.dart | 116 +++++++++++++++++++--------- lib/src/database/hive_database.dart | 8 +- 2 files changed, 82 insertions(+), 42 deletions(-) diff --git a/lib/src/client.dart b/lib/src/client.dart index 379567ad..f52f6865 100644 --- a/lib/src/client.dart +++ b/lib/src/client.dart @@ -877,44 +877,8 @@ class Client extends MatrixApi { if (accessToken == null || homeserver == null || _userID == null) { if (legacyDatabaseBuilder != null) { - Logs().i('Check legacy database for migration data...'); - final legacyDatabase = await legacyDatabaseBuilder(this); - final migrateClient = await legacyDatabase.getClient(clientName); - if (migrateClient != null) { - Logs().i('Found data in the legacy database!'); - _id = migrateClient['client_id']; - await database.insertClient( - clientName, - migrateClient['homeserver_url'], - migrateClient['token'], - migrateClient['user_id'], - migrateClient['device_id'], - migrateClient['device_name'], - null, - migrateClient['olm_account'], - ); - for (final type in cacheTypes) { - final ssssCache = await legacyDatabase.getSSSSCache(_id, type); - if (ssssCache != null) { - Logs().d('Migrate $type'); - await database.storeSSSSCache( - _id, - type, - ssssCache.keyId, - ssssCache.ciphertext, - ssssCache.content, - ); - } - } - - await legacyDatabase.clear(_id); - await legacyDatabaseDestroyer?.call(this); - } - await legacyDatabase.close(); - if (migrateClient != null) { - _initLock = false; - return init(); - } + await _migrateFromLegacyDatabase(); + if (isLogged()) return; } // we aren't logged in encryption?.dispose(); @@ -2109,6 +2073,82 @@ sort order of ${prevState.sortOrder}. This should never happen...'''); } return; } + + Future _migrateFromLegacyDatabase() async { + Logs().i('Check legacy database for migration data...'); + final legacyDatabase = await legacyDatabaseBuilder(this); + final migrateClient = await legacyDatabase.getClient(clientName); + + if (migrateClient != null) { + Logs().i('Found data in the legacy database!'); + _id = migrateClient['client_id']; + await database.insertClient( + clientName, + migrateClient['homeserver_url'], + migrateClient['token'], + migrateClient['user_id'], + migrateClient['device_id'], + migrateClient['device_name'], + null, + migrateClient['olm_account'], + ); + Logs().d('Migrate SSSSCache...'); + for (final type in cacheTypes) { + final ssssCache = await legacyDatabase.getSSSSCache(_id, type); + if (ssssCache != null) { + Logs().d('Migrate $type...'); + await database.storeSSSSCache( + _id, + type, + ssssCache.keyId, + ssssCache.ciphertext, + ssssCache.content, + ); + } + } + Logs().d('Migrate Device Keys...'); + final userDeviceKeys = await legacyDatabase.getUserDeviceKeys(this); + for (final userId in userDeviceKeys.keys) { + Logs().d('Migrate Device Keys of user $userId...'); + final deviceKeysList = userDeviceKeys[userId]; + for (final crossSigningKey in deviceKeysList.crossSigningKeys.values) { + Logs().d( + 'Migrate cross signing key with usage ${crossSigningKey.usage} and verified ${crossSigningKey.directVerified}...'); + await database.storeUserCrossSigningKey( + _id, + userId, + crossSigningKey.publicKey, + jsonEncode(crossSigningKey.toJson()), + crossSigningKey.directVerified, + crossSigningKey.blocked, + ); + } + for (final deviceKeys in deviceKeysList.deviceKeys.values) { + Logs().d('Migrate device keys for ${deviceKeys.deviceId}...'); + await database.storeUserDeviceKey( + _id, + userId, + deviceKeys.deviceId, + jsonEncode(deviceKeys.toJson()), + deviceKeys.directVerified, + deviceKeys.blocked, + deviceKeys.lastActive.millisecondsSinceEpoch, + ); + } + Logs().d('Migrate user device keys info...'); + await database.storeUserDeviceKeysInfo( + _id, userId, deviceKeysList.outdated); + } + + await legacyDatabase.clear(_id); + await legacyDatabaseDestroyer?.call(this); + } + await legacyDatabase.close(); + _initLock = false; + if (migrateClient != null) { + return init(); + } + } } class SdkError { diff --git a/lib/src/database/hive_database.dart b/lib/src/database/hive_database.dart index 70c70f6e..6ba48c81 100644 --- a/lib/src/database/hive_database.dart +++ b/lib/src/database/hive_database.dart @@ -933,8 +933,8 @@ class FamedlySdkHiveDatabase extends DatabaseApi { 'user_id': userId, 'public_key': publicKey, 'content': content, - 'verified': verified ?? false, - 'blocked': blocked ?? false, + 'verified': verified, + 'blocked': blocked, }, ); } @@ -946,8 +946,8 @@ class FamedlySdkHiveDatabase extends DatabaseApi { 'user_id': userId, 'device_id': deviceId, 'content': content, - 'verified': verified ?? false, - 'blocked': blocked ?? false, + 'verified': verified, + 'blocked': blocked, 'last_active': lastActive, 'last_sent_message': '', });