Try migrating old auth to keychain

This commit is contained in:
Marcus Kida 2023-06-05 15:53:27 +02:00 committed by Nathan Mattes
parent 4c9c34b6ce
commit 55afa02b52
5 changed files with 54 additions and 25 deletions

View File

@ -18,7 +18,6 @@ class AppDelegate: UIResponder, UIApplicationDelegate {
let appContext = AppContext()
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
AuthenticationServiceProvider.shared.migrateLegacyAuthenticationsIfRequired(in: appContext.managedObjectContext)
AuthenticationServiceProvider.shared.restore()
AppSecret.default.register()

View File

@ -17,7 +17,7 @@ final class SendPostIntentHandler: NSObject {
var disposeBag = Set<AnyCancellable>()
let coreDataStack = CoreDataStack()
let coreDataStack = CoreDataStack(isInMemory: true)
lazy var managedObjectContext = coreDataStack.persistentContainer.viewContext
lazy var api: APIService = {
let backgroundManagedObjectContext = coreDataStack.newTaskContext()

View File

@ -22,10 +22,15 @@ public final class CoreDataStack {
self.storeDescriptions = storeDescriptions
}
public convenience init(databaseName: String = "shared") {
public convenience init(databaseName: String = "shared", isInMemory: Bool) {
let storeURL = URL.storeURL(for: AppName.groupID, databaseName: databaseName)
let storeDescription = NSPersistentStoreDescription(url: storeURL)
storeDescription.url = URL(fileURLWithPath: "/dev/null") /// in-memory store with all features in favor of NSInMemoryStoreType
let storeDescription: NSPersistentStoreDescription
if isInMemory {
storeDescription = NSPersistentStoreDescription(url: URL(string: "file:///dev/null")!) /// in-memory store with all features in favor of NSInMemoryStoreType
} else {
storeDescription = NSPersistentStoreDescription(url: storeURL)
storeDescription.isReadOnly = true
}
self.init(persistentStoreDescriptions: [storeDescription])
}
@ -123,16 +128,18 @@ extension CoreDataStack {
}
}
extension CoreDataStack {
public func rebuild() {
public extension CoreDataStack {
func tearDown() {
let oldStoreURL = persistentContainer.persistentStoreCoordinator.url(for: persistentContainer.persistentStoreCoordinator.persistentStores.first!)
try! persistentContainer.persistentStoreCoordinator.destroyPersistentStore(at: oldStoreURL, ofType: NSSQLiteStoreType, options: nil)
}
func rebuild() {
tearDown()
CoreDataStack.load(persistentContainer: persistentContainer) { [weak self] in
guard let self = self else { return }
self.didFinishLoad.value = true
}
}
}

View File

@ -47,7 +47,14 @@ public class AppContext: ObservableObject {
.eraseToAnyPublisher()
public init() {
let _coreDataStack = CoreDataStack()
/// Migrate existing Authentications to new Keychain-Based format
// var _legacyCoreDataStack: CoreDataStack? = CoreDataStack(isInMemory: false)
// AuthenticationServiceProvider.shared.migrateLegacyAuthenticationsIfRequired(in: _legacyCoreDataStack!.persistentContainer.viewContext)
// _legacyCoreDataStack!.tearDown()
// _legacyCoreDataStack = nil
let _coreDataStack = CoreDataStack(isInMemory: true)
let _managedObjectContext = _coreDataStack.persistentContainer.viewContext
let _backgroundManagedObjectContext = _coreDataStack.persistentContainer.newBackgroundContext()
coreDataStack = _coreDataStack

View File

@ -69,27 +69,43 @@ public extension AuthenticationServiceProvider {
}
func migrateLegacyAuthenticationsIfRequired(in context: NSManagedObjectContext) {
guard !userDefaults.didMigrateAuthentications else { return }
// guard !userDefaults.didMigrateAuthentications else { return }
defer { userDefaults.didMigrateAuthentications = true }
do {
let request = NSFetchRequest<MastodonAuthenticationLegacy>(entityName: "MastodonAuthentication")
let request = NSFetchRequest<NSManagedObject>(entityName: "MastodonAuthentication")
let legacyAuthentications = try context.fetch(request)
self.authentications = legacyAuthentications.map { auth in
MastodonAuthentication(
identifier: auth.identifier,
domain: auth.domain,
username: auth.username,
appAccessToken: auth.appAccessToken,
userAccessToken: auth.userAccessToken,
clientID: auth.clientID,
clientSecret: auth.clientSecret,
createdAt: auth.createdAt,
updatedAt: auth.updatedAt,
activedAt: auth.activedAt,
userID: auth.userID
self.authentications = legacyAuthentications.compactMap { auth -> MastodonAuthentication? in
guard
let identifier = auth.value(forKey: "identifier") as? UUID,
let domain = auth.value(forKey: "domain") as? String,
let username = auth.value(forKey: "username") as? String,
let appAccessToken = auth.value(forKey: "appAccessToken") as? String,
let userAccessToken = auth.value(forKey: "userAccessToken") as? String,
let clientID = auth.value(forKey: "clientID") as? String,
let clientSecret = auth.value(forKey: "clientSecret") as? String,
let createdAt = auth.value(forKey: "createdAt") as? Date,
let updatedAt = auth.value(forKey: "updatedAt") as? Date,
let activedAt = auth.value(forKey: "activedAt") as? Date,
let userID = auth.value(forKey: "userID") as? String
else {
return nil
}
return MastodonAuthentication(
identifier: identifier,
domain: domain,
username: username,
appAccessToken: appAccessToken,
userAccessToken: userAccessToken,
clientID: clientID,
clientSecret: clientSecret,
createdAt: createdAt,
updatedAt: updatedAt,
activedAt: activedAt,
userID: userID
)
}
} catch {