Last active
December 4, 2017 07:43
-
-
Save Kleemann/e4a425816157bde074b32d51440df7ab to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| // | |
| // DatabaseWorker.swift | |
| // Readlst | |
| // | |
| // Created by Mads Kleemann on 04/08/2017. | |
| // Copyright (c) 2017 Readlst. All rights reserved. | |
| // | |
| import UIKit | |
| import RealmSwift | |
| class DatabaseWorker { | |
| fileprivate let defaultTimeout = 2.5 | |
| func save<T: Object>(objects: [T], updateIfExsists: Bool = true, completion: (() -> Void)? = .none) throws { | |
| let semaphore = DispatchSemaphore(value: 0) | |
| do { | |
| let realm = try Realm() | |
| try realm.write { | |
| realm.add(objects, update: updateIfExsists) | |
| semaphore.signal() | |
| } | |
| _ = semaphore.wait(timeout: .now() + defaultTimeout) | |
| completion?() | |
| } catch let error { | |
| throw error | |
| } | |
| } | |
| func getObjects<T: Object>(withPredicate predicate: NSPredicate? = .none) -> [T] { | |
| let objects: Results<T>? = getList(withPredicate: predicate) | |
| return objects == .none ? [] : Array(objects!) | |
| } | |
| func getObject<T: Object>(withPredicate predicate: NSPredicate) -> T? { | |
| let object: T? = getList(withPredicate: predicate)?.first | |
| return object | |
| } | |
| func delete<T: Object>(ofType type: T.Type, withPredicate predicate: NSPredicate? = .none, completion: (() -> Void)? = .none) throws { | |
| guard let objectsToDelete: Results<T> = self.getList(withPredicate: predicate), objectsToDelete.count > 0 else { | |
| //We dont have any objects of the type so we just complete | |
| completion?() | |
| return | |
| } | |
| let semaphore = DispatchSemaphore(value: 0) | |
| do { | |
| let realm = try Realm() | |
| try realm.write { | |
| realm.delete(objectsToDelete) | |
| semaphore.signal() | |
| } | |
| _ = semaphore.wait(timeout: .now() + defaultTimeout) | |
| completion?() | |
| } catch let error { | |
| throw error | |
| } | |
| } | |
| func delete(_ object:Object) throws { | |
| do { | |
| let realm = try Realm() | |
| try realm.write { | |
| realm.delete(object) | |
| } | |
| } catch let error { | |
| throw error | |
| } | |
| } | |
| func replaceAllObjects<T: Object>(ofType: T.Type, withObjects newObjects: [T], completion: (() -> Void)? = .none) throws { | |
| guard let objectsInDatabase: Results<T> = getList(), objectsInDatabase.count > 0 else { | |
| //We dont have any object in the database of type, just save the new objects | |
| do { | |
| try save(objects: newObjects, completion: completion) | |
| } catch let error { | |
| throw error | |
| } | |
| return | |
| } | |
| let objectsToUpdate = newObjects.filter { objectsInDatabase.contains($0) } | |
| let objectsToAdd = newObjects.filter { !objectsInDatabase.contains($0) } | |
| let objectsToDelete = objectsInDatabase.filter { !newObjects.contains($0) } | |
| let semaphore = DispatchSemaphore(value: 0) | |
| do { | |
| let realm = try Realm() | |
| try realm.write { | |
| realm.add(objectsToUpdate, update: true) | |
| realm.add(objectsToAdd) | |
| realm.delete(objectsToDelete) | |
| semaphore.signal() | |
| } | |
| _ = semaphore.wait(timeout: .now() + defaultTimeout) | |
| completion?() | |
| } catch let error { | |
| throw error | |
| } | |
| } | |
| func addNotification<T:Object>(forObject objectType: T.Type, | |
| withPredicate predicate: NSPredicate? = .none, | |
| sortedBy sorting: (sortKey: String, ascending: Bool)? = .none, | |
| andBlock block: @escaping (RealmCollectionChange<Results<T>>) -> Void) -> NotificationToken? { | |
| var objectList: Results<T>? = getList(withPredicate: predicate) | |
| if let sorting = sorting { | |
| objectList = objectList?.sorted(byKeyPath: sorting.sortKey, ascending: sorting.ascending) | |
| } | |
| return objectList?.observe({ (changes) in | |
| block(changes) | |
| }) | |
| } | |
| func write(_ block: () -> Void) throws { | |
| do { | |
| let realm = try Realm() | |
| try realm.write { | |
| block() | |
| } | |
| } catch let error { | |
| throw error | |
| } | |
| } | |
| fileprivate func getList<T: Object>(withPredicate predicate: NSPredicate? = .none) -> Results<T>? { | |
| let realm = try? Realm() | |
| var objects: Results<T>? = .none | |
| if let p = predicate { | |
| objects = realm?.objects(T.self).filter(p) | |
| } else { | |
| objects = realm?.objects(T.self) | |
| } | |
| return objects | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment