diff --git a/Sources/XXMessengerClient/Messenger/Functions/MessengerRestoreBackup.swift b/Sources/XXMessengerClient/Messenger/Functions/MessengerRestoreBackup.swift new file mode 100644 index 0000000000000000000000000000000000000000..02b45c614052e61e84b8db33b43197de240abd09 --- /dev/null +++ b/Sources/XXMessengerClient/Messenger/Functions/MessengerRestoreBackup.swift @@ -0,0 +1,75 @@ +import Foundation +import XXClient +import XCTestDynamicOverlay + +public struct MessengerRestoreBackup { + public var run: (Data, String) throws -> BackupParams + + public func callAsFunction( + backupData: Data, + backupPassphrase: String + ) throws -> BackupParams { + try run(backupData, backupPassphrase) + } +} + +extension MessengerRestoreBackup { + public static func live(_ env: MessengerEnvironment) -> MessengerRestoreBackup { + MessengerRestoreBackup { backupData, backupPassphrase in + let storageDir = env.storageDir + do { + let ndfData = try env.downloadNDF(env.ndfEnvironment) + let password = env.generateSecret() + try env.passwordStorage.save(password) + try env.fileManager.removeDirectory(storageDir) + try env.fileManager.createDirectory(storageDir) + let report = try env.newCMixFromBackup( + ndfJSON: String(data: ndfData, encoding: .utf8)!, + storageDir: storageDir, + backupPassphrase: backupPassphrase, + sessionPassword: password, + backupFileContents: backupData + ) + let cMix = try env.loadCMix( + storageDir: storageDir, + password: password, + cMixParamsJSON: env.getCMixParams() + ) + let e2e = try env.login( + cMixId: cMix.getId(), + authCallbacks: env.authCallbacks.registered(), + identity: try cMix.makeReceptionIdentity(legacy: true), + e2eParamsJSON: env.getE2EParams() + ) + let decoder = JSONDecoder() + let paramsData = report.params.data(using: .utf8)! + let params = try decoder.decode(BackupParams.self, from: paramsData) + let ud = try env.newUdManagerFromBackup( + params: NewUdManagerFromBackup.Params( + e2eId: e2e.getId(), + username: Fact(type: .username, value: params.username), + email: params.email.map { Fact(type: .email, value: $0) }, + phone: params.phone.map { Fact(type: .phone, value: $0) }, + cert: env.udCert ?? e2e.getUdCertFromNdf(), + contact: env.udContact ?? (try e2e.getUdContactFromNdf()), + address: env.udAddress ?? e2e.getUdAddressFromNdf() + ), + follower: UdNetworkStatus { cMix.networkFollowerStatus() } + ) + env.cMix.set(cMix) + env.e2e.set(e2e) + env.ud.set(ud) + return params + } catch { + try? env.fileManager.removeDirectory(storageDir) + throw error + } + } + } +} + +extension MessengerRestoreBackup { + public static let unimplemented = MessengerRestoreBackup( + run: XCTUnimplemented("\(Self.self)") + ) +} diff --git a/Sources/XXMessengerClient/Messenger/Messenger.swift b/Sources/XXMessengerClient/Messenger/Messenger.swift index 77f7f1e52f85af6d083f3b26916d8432643ab6a4..ad3fff797d257b6d7014b67792f90b87a74f51c8 100644 --- a/Sources/XXMessengerClient/Messenger/Messenger.swift +++ b/Sources/XXMessengerClient/Messenger/Messenger.swift @@ -6,6 +6,7 @@ public struct Messenger { public var ud: Stored<UserDiscovery?> public var isCreated: MessengerIsCreated public var create: MessengerCreate + public var restoreBackup: MessengerRestoreBackup public var isLoaded: MessengerIsLoaded public var load: MessengerLoad public var registerAuthCallbacks: MessengerRegisterAuthCallbacks @@ -37,6 +38,7 @@ extension Messenger { ud: env.ud, isCreated: .live(env), create: .live(env), + restoreBackup: .live(env), isLoaded: .live(env), load: .live(env), registerAuthCallbacks: .live(env), @@ -69,6 +71,7 @@ extension Messenger { ud: .unimplemented(), isCreated: .unimplemented, create: .unimplemented, + restoreBackup: .unimplemented, isLoaded: .unimplemented, load: .unimplemented, registerAuthCallbacks: .unimplemented, diff --git a/Sources/XXMessengerClient/Messenger/MessengerEnvironment.swift b/Sources/XXMessengerClient/Messenger/MessengerEnvironment.swift index f125c1ef3ae705a1dde5d8e9ff1dc4467e25044c..00ab6338b1731987b1f27b8c2c17da3bef8ed695 100644 --- a/Sources/XXMessengerClient/Messenger/MessengerEnvironment.swift +++ b/Sources/XXMessengerClient/Messenger/MessengerEnvironment.swift @@ -20,7 +20,9 @@ public struct MessengerEnvironment { public var multiLookupUD: MultiLookupUD public var ndfEnvironment: NDFEnvironment public var newCMix: NewCMix + public var newCMixFromBackup: NewCMixFromBackup public var newOrLoadUd: NewOrLoadUd + public var newUdManagerFromBackup: NewUdManagerFromBackup public var passwordStorage: PasswordStorage public var registerForNotifications: RegisterForNotifications public var searchUD: SearchUD @@ -58,7 +60,9 @@ extension MessengerEnvironment { multiLookupUD: .live(), ndfEnvironment: .mainnet, newCMix: .live, + newCMixFromBackup: .live, newOrLoadUd: .live, + newUdManagerFromBackup: .live, passwordStorage: .keychain, registerForNotifications: .live, searchUD: .live, @@ -91,7 +95,9 @@ extension MessengerEnvironment { multiLookupUD: .unimplemented, ndfEnvironment: .unimplemented, newCMix: .unimplemented, + newCMixFromBackup: .unimplemented, newOrLoadUd: .unimplemented, + newUdManagerFromBackup: .unimplemented, passwordStorage: .unimplemented, registerForNotifications: .unimplemented, searchUD: .unimplemented, diff --git a/Sources/XXMessengerClient/Utils/BackupParams.swift b/Sources/XXMessengerClient/Utils/BackupParams.swift new file mode 100644 index 0000000000000000000000000000000000000000..28523748f8312a1267bbaa12e034f814b81b3e7c --- /dev/null +++ b/Sources/XXMessengerClient/Utils/BackupParams.swift @@ -0,0 +1,17 @@ +import Foundation + +public struct BackupParams: Codable { + public init( + email: String?, + phone: String?, + username: String + ) { + self.email = email + self.phone = phone + self.username = username + } + + public var email: String? + public var phone: String? + public var username: String +}