Merge pull request #5501 from keymanapp/fix/ios/cherry/force-manager-init-preinstall

fix(ios/engine): engine migration always precedes installs 🍒
This commit is contained in:
Joshua Horton 2021-07-30 08:09:38 +07:00 • committed by GitHub
commit 79c31d0643
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 44 additions and 14 deletions

View file

@ -201,20 +201,11 @@ public class Manager: NSObject, UIGestureRecognizerDelegate {
URLProtocol.registerClass(KeymanURLProtocol.self)
Migrations.migrate(storage: Storage.active)
Migrations.updateResources(storage: Storage.active)
if Storage.active.userDefaults.userKeyboards?.isEmpty ?? true {
Storage.active.userDefaults.userKeyboards = [Defaults.keyboard]
// Ensure the default keyboard is installed in this case.
do {
try Storage.active.installDefaultKeyboard(from: Resources.bundle)
} catch {
log.error("Failed to copy default keyboard from bundle: \(error)")
}
}
Migrations.engineVersion = Version.latestFeature
/**
* As of 14.0, ResourceFileManager is responsible for handlng resources... including
* any necessary "migration" of their internal storage structure & tracked metadata.
*/
ResourceFileManager.shared.runMigrationsIfNeeded()
if Util.isSystemKeyboard || Storage.active.userDefaults.bool(forKey: Key.keyboardPickerDisplayed) {
isKeymanHelpOn = false

View file

@ -17,9 +17,38 @@ import UIKit
public class ResourceFileManager {
public static let shared = ResourceFileManager()
private var haveRunMigrations: Bool = false
fileprivate init() {
}
func runMigrationsIfNeeded() {
if !haveRunMigrations {
// Set here in order to prevent recursively calling itself in case
// Migrations itself needs to use installation methods.
haveRunMigrations = true
// We must make sure that all resources are properly migrated before
// allowing any new resources to be installed.
Migrations.migrate(storage: Storage.active)
Migrations.updateResources(storage: Storage.active)
if Storage.active.userDefaults.userKeyboards?.isEmpty ?? true {
Storage.active.userDefaults.userKeyboards = [Defaults.keyboard]
// Ensure the default keyboard is installed in this case.
do {
try Storage.active.installDefaultKeyboard(from: Resources.bundle)
} catch {
log.error("Failed to copy default keyboard from bundle: \(error)")
}
}
Migrations.engineVersion = Version.latestFeature
}
haveRunMigrations = true
}
public var installedPackages: [KeymanPackage] {
let userResources = Storage.active.userDefaults.userResources ?? []
@ -328,6 +357,14 @@ public class ResourceFileManager {
throw KMPError.resourceNotInPackage
}
// Resources should only be installed after Migrations have been run.
// Otherwise, the Migrations engine may misinterpret the installed format
// on an app's first install.
//
// It is possible for a KeymanEngine framework consumer to reach this point
// without `Manager.init` having been run.
runMigrationsIfNeeded()
do {
try copyWithOverwrite(from: package.sourceFolder,
to: Storage.active.packageDir(for: package)!)

View file

@ -20,6 +20,8 @@ class AppDelegate: UIResponder, UIApplicationDelegate {
KeymanEngine.log.logAppDetails()
// Replace with your application group id
// Ensure this happens before installing any keyboards or models within the engine
// whenever using App Group Identifiers.
Manager.applicationGroupIdentifier = "group.KMSample"
return true
}