简体   繁体   中英

Can I delete a Realm instead of doing a migration?

We're using Realm as a cache, so we had an idea to just delete the Realm and start over if we make changes to any of the schemas in Realm.

Is this a good strategy? Anything to watch out for?

Here's some sample code:

class RealmHelper {
    static let SCHEMA_NUMBER = 5
    static let SCHEMA_NUMBER_KEY = "Neutum:RealmHelper:SCHEMA_NUMBER"

    /// Realm property. This is a computed property to keep thread-safety,
    static var realm: Realm = {
        let defaults = UserDefaults.standard
        // By default is 0
        let schemaNumber = defaults.integer(forKey: SCHEMA_NUMBER_KEY)

        if schemaNumber < SCHEMA_NUMBER {
            RealmHelper.dangerousDeleteAllRealmData()
            defaults.set(SCHEMA_NUMBER, forKey: SCHEMA_NUMBER_KEY)
        }

        return try! Realm()
    }()

    /// Should only be used in the static intializer. That is, this will cause
    /// issues if there are any active instances of Realm.
    ///
    /// See the documentation: https://realm.io/docs/swift/latest/#deleting-realm-files
    static func dangerousDeleteAllRealmData() {
        let realmURL = Realm.Configuration.defaultConfiguration.fileURL!
        do {
            try FileManager.default.removeItem(at: realmURL)

            var lockURL = realmURL
            lockURL.appendPathComponent("lock")
            try FileManager.default.removeItem(at: lockURL)

            var logAURL = realmURL
            logAURL.appendPathComponent("log_a")
            try FileManager.default.removeItem(at: logAURL)

            var logBURL = realmURL
            logBURL.appendPathComponent("log_b")
            try FileManager.default.removeItem(at: logBURL)

            var noteURL = realmURL
            noteURL.appendPathComponent("note")
            try FileManager.default.removeItem(at: noteURL)
        } catch {
            // Do nothing (apparently can't even log ErrorType)
        }
    }
}

I would strongly recommend to just set deleteRealmIfMigrationNeeded to true in your Realm.Configuration .

Documentation: https://realm.io/docs/swift/latest/api/Classes/Realm/Configuration.html#/s:vVC10RealmSwift5Realm13Configuration28deleteRealmIfMigrationNeededSb

My extension when I use Realm as a cache to prevent migration problems:

extension Realm
{
    static var cacheConfig: Realm.Configuration {
        let cacheDirs = NSSearchPathForDirectoriesInDomains(.cachesDirectory, .userDomainMask, true)
        let cacheURL = URL(fileURLWithPath: cacheDirs.first!)

        return Realm.Configuration(
            fileURL: cacheURL.appendingPathComponent("cache.realm"),
            inMemoryIdentifier: nil,
            syncConfiguration: nil,
            encryptionKey: nil,
            readOnly: false,
            schemaVersion: 0,
            migrationBlock: nil,
            deleteRealmIfMigrationNeeded: true,
            objectTypes: nil
        )
    }

    static var cache: Realm {
        do {
            return try Realm(configuration: Realm.cacheConfig)
        }
        catch let error as NSError {
            ... handle error ...
        }
    }
}

And just use Realm.cache... when I would like to access the cache.

Like: Realm.cache.objects(Responses.self)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM