From 55dee6ec2f62423ccc4112a72a129837beaf0fc1 Mon Sep 17 00:00:00 2001 From: John Rommel Estropia Date: Sat, 28 Feb 2015 11:32:41 +0900 Subject: [PATCH] refactor logging functions --- HardcoreData.xcodeproj/project.pbxproj | 4 + HardcoreData/DataStack.swift | 96 +++++++++---------- HardcoreData/DataTransaction.swift | 2 +- HardcoreData/HardcoreData+Logging.swift | 75 +++++++++++++++ HardcoreData/HardcoreData.swift | 42 -------- .../NSManagedObject+Transaction.swift | 14 +-- .../NSManagedObjectContext+HardcoreData.swift | 16 ++-- .../NSManagedObjectContext+Querying.swift | 12 ++- .../NSManagedObjectContext+Transaction.swift | 4 +- HardcoreData/SortedBy.swift | 2 +- HardcoreData/Where.swift | 2 +- 11 files changed, 151 insertions(+), 118 deletions(-) create mode 100644 HardcoreData/HardcoreData+Logging.swift diff --git a/HardcoreData.xcodeproj/project.pbxproj b/HardcoreData.xcodeproj/project.pbxproj index 04e87d6..022c97a 100644 --- a/HardcoreData.xcodeproj/project.pbxproj +++ b/HardcoreData.xcodeproj/project.pbxproj @@ -23,6 +23,7 @@ B5D022661A90CD340070CA63 /* DataStack+Transaction.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D022651A90CD340070CA63 /* DataStack+Transaction.swift */; }; B5D19BFB1AA14063001D1A99 /* AsynchronousDataTransaction.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D19BFA1AA14063001D1A99 /* AsynchronousDataTransaction.swift */; }; B5D19BFF1AA14351001D1A99 /* SynchronousDataTransaction.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D19BFE1AA14351001D1A99 /* SynchronousDataTransaction.swift */; }; + B5D19C011AA15E1F001D1A99 /* HardcoreData+Logging.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D19C001AA15E1F001D1A99 /* HardcoreData+Logging.swift */; }; B5D1E22A19FA9E63003B2874 /* PersistentStoreResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D1E22919FA9E63003B2874 /* PersistentStoreResult.swift */; }; B5D1E22C19FA9FBC003B2874 /* NSError+HardcoreData.swift in Sources */ = {isa = PBXBuildFile; fileRef = B5D1E22B19FA9FBC003B2874 /* NSError+HardcoreData.swift */; }; B5D372841A39CD6900F583D9 /* Model.xcdatamodeld in Sources */ = {isa = PBXBuildFile; fileRef = B5D372821A39CD6900F583D9 /* Model.xcdatamodeld */; }; @@ -90,6 +91,7 @@ B5D022651A90CD340070CA63 /* DataStack+Transaction.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "DataStack+Transaction.swift"; sourceTree = ""; }; B5D19BFA1AA14063001D1A99 /* AsynchronousDataTransaction.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AsynchronousDataTransaction.swift; sourceTree = ""; }; B5D19BFE1AA14351001D1A99 /* SynchronousDataTransaction.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SynchronousDataTransaction.swift; sourceTree = ""; }; + B5D19C001AA15E1F001D1A99 /* HardcoreData+Logging.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "HardcoreData+Logging.swift"; sourceTree = ""; }; B5D1E22919FA9E63003B2874 /* PersistentStoreResult.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = PersistentStoreResult.swift; sourceTree = ""; }; B5D1E22B19FA9FBC003B2874 /* NSError+HardcoreData.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "NSError+HardcoreData.swift"; sourceTree = ""; }; B5D372831A39CD6900F583D9 /* Model.xcdatamodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcdatamodel; path = Model.xcdatamodel; sourceTree = ""; }; @@ -307,6 +309,7 @@ children = ( B5F409E81A8B11CE00A228EA /* HardcoreDataLogger.swift */, B5F409EA1A8B199600A228EA /* DefaultLogger.swift */, + B5D19C001AA15E1F001D1A99 /* HardcoreData+Logging.swift */, ); name = Logging; sourceTree = ""; @@ -443,6 +446,7 @@ buildActionMask = 2147483647; files = ( B5CFF24019FD383100D6DFC4 /* DataTransaction.swift in Sources */, + B5D19C011AA15E1F001D1A99 /* HardcoreData+Logging.swift in Sources */, B5D399F519FCF4E0000E91BB /* NSPersistentStoreCoordinator+HardcoreData.swift in Sources */, B5CFD36E1A0775F000B7885F /* SaveResult.swift in Sources */, B5D022661A90CD340070CA63 /* DataStack+Transaction.swift in Sources */, diff --git a/HardcoreData/DataStack.swift b/HardcoreData/DataStack.swift index bbed98a..0097a9e 100644 --- a/HardcoreData/DataStack.swift +++ b/HardcoreData/DataStack.swift @@ -94,7 +94,7 @@ public class DataStack { public func addInMemoryStore(configuration: String? = nil) -> PersistentStoreResult { let coordinator = self.coordinator; - var persistentStoreError: NSError? + var error: NSError? var store: NSPersistentStore? coordinator.performSynchronously { @@ -104,7 +104,7 @@ public class DataStack { configuration: configuration, URL: nil, options: nil, - error: &persistentStoreError) + error: &error) } if let store = store { @@ -112,20 +112,20 @@ public class DataStack { return PersistentStoreResult(store) } - if let error = persistentStoreError { + if let error = error { HardcoreData.handleError( error, - "Failed to add in-memory NSPersistentStore.") + "Failed to add in-memory \(NSPersistentStore.self).") return PersistentStoreResult(error) } else { HardcoreData.handleError( NSError(hardcoreDataErrorCode: .UnknownError), - "Failed to add in-memory NSPersistentStore.") + "Failed to add in-memory \(NSPersistentStore.self).") + return PersistentStoreResult(.UnknownError) } - return PersistentStoreResult(.UnknownError) } /** @@ -174,7 +174,8 @@ public class DataStack { HardcoreData.handleError( NSError(hardcoreDataErrorCode: .DifferentPersistentStoreExistsAtURL), - "Failed to add SQLite NSPersistentStore at \"\(fileURL)\" because a different NSPersistentStore at that URL already exists.") + "Failed to add SQLite \(NSPersistentStore.self) at \"\(fileURL)\" because a different \(NSPersistentStore.self) at that URL already exists.") + return PersistentStoreResult(.DifferentPersistentStoreExistsAtURL) } @@ -187,7 +188,7 @@ public class DataStack { error: &directoryError) { HardcoreData.handleError( - directoryError!, + directoryError ?? NSError(hardcoreDataErrorCode: .UnknownError), "Failed to create directory for SQLite store at \"\(fileURL)\".") return PersistentStoreResult(directoryError!) } @@ -211,54 +212,45 @@ public class DataStack { return PersistentStoreResult(store) } - if let error = persistentStoreError { - - if resetStoreOnMigrationFailure - && (error.code == NSPersistentStoreIncompatibleVersionHashError - || error.code == NSMigrationMissingSourceModelError) - && error.domain == NSCocoaErrorDomain { + if let error = persistentStoreError + where ( + resetStoreOnMigrationFailure + && (error.code == NSPersistentStoreIncompatibleVersionHashError + || error.code == NSMigrationMissingSourceModelError) + && error.domain == NSCocoaErrorDomain + ) { + + fileManager.removeItemAtURL(fileURL, error: nil) + fileManager.removeItemAtPath( + fileURL.path!.stringByAppendingString("-shm"), + error: nil) + fileManager.removeItemAtPath( + fileURL.path!.stringByAppendingString("-wal"), + error: nil) + + var store: NSPersistentStore? + coordinator.performSynchronously { - fileManager.removeItemAtURL(fileURL, error: nil) - fileManager.removeItemAtPath( - fileURL.path!.stringByAppendingString("-shm"), - error: nil) - fileManager.removeItemAtPath( - fileURL.path!.stringByAppendingString("-wal"), - error: nil) + store = coordinator.addPersistentStoreWithType( + NSSQLiteStoreType, + configuration: configuration, + URL: fileURL, + options: [NSSQLitePragmasOption: ["WAL": "journal_mode"], + NSInferMappingModelAutomaticallyOption: true, + NSMigratePersistentStoresAutomaticallyOption: automigrating], + error: &persistentStoreError) + } + + if let store = store { - var store: NSPersistentStore? - coordinator.performSynchronously { - - store = coordinator.addPersistentStoreWithType( - NSSQLiteStoreType, - configuration: configuration, - URL: fileURL, - options: [NSSQLitePragmasOption: ["WAL": "journal_mode"], - NSInferMappingModelAutomaticallyOption: true, - NSMigratePersistentStoresAutomaticallyOption: automigrating], - error: &persistentStoreError) - } - - if let store = store { - - return PersistentStoreResult(store) - } - } + return PersistentStoreResult(store) + } } - if let error = persistentStoreError { - - HardcoreData.handleError( - error, - "Failed to add SQLite NSPersistentStore at \"\(fileURL)\".") - return PersistentStoreResult(error) - } - else { - - HardcoreData.handleError( - NSError(hardcoreDataErrorCode: .UnknownError), - "Failed to add SQLite NSPersistentStore at \"\(fileURL)\".") - } + HardcoreData.handleError( + persistentStoreError ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed to add SQLite \(NSPersistentStore.self) at \"\(fileURL)\".") + return PersistentStoreResult(.UnknownError) } diff --git a/HardcoreData/DataTransaction.swift b/HardcoreData/DataTransaction.swift index ce9e490..80ae333 100644 --- a/HardcoreData/DataTransaction.swift +++ b/HardcoreData/DataTransaction.swift @@ -46,7 +46,7 @@ public /*abstract*/ class DataTransaction { public func create(entity: T.Type) -> T { HardcoreData.assert(self.transactionQueue.isCurrentExecutionContext() == true, "Attempted to create an entity of type \(entity) outside a transaction queue.") - HardcoreData.assert(!self.isCommitted, "Attempted to create an NSManagedObject from an already committed \(self.dynamicType).") + HardcoreData.assert(!self.isCommitted, "Attempted to create an entity of type \(entity) from an already committed \(self.dynamicType).") return T.createInContext(self.context) } diff --git a/HardcoreData/HardcoreData+Logging.swift b/HardcoreData/HardcoreData+Logging.swift new file mode 100644 index 0000000..3dd8ffa --- /dev/null +++ b/HardcoreData/HardcoreData+Logging.swift @@ -0,0 +1,75 @@ +// +// HardcoreData+Logging.swift +// HardcoreData +// +// Copyright (c) 2015 John Rommel Estropia +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in all +// copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. +// + +import Foundation + + +// MARK: - HardcoreData + +public extension HardcoreData { + + // MARK: Public + + /** + The HardcoreDataLogger instance to be used. The default logger is an instance of a DefaultLogger. + */ + public static var logger: HardcoreDataLogger = DefaultLogger() + + + // MARK: Internal + + internal static func log(level: LogLevel, message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { + + self.logger.log( + level: level, + message: message, + fileName: fileName, + lineNumber: + lineNumber, + functionName: + functionName + ) + } + + internal static func handleError(error: NSError, _ message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { + + self.logger.handleError( + error: error, + message: message, + fileName: fileName, + lineNumber: lineNumber, + functionName: functionName) + } + + internal static func assert(@autoclosure condition: () -> Bool, _ message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { + + self.logger.assert( + condition, + message: message, + fileName: fileName, + lineNumber: lineNumber, + functionName: functionName) + } +} \ No newline at end of file diff --git a/HardcoreData/HardcoreData.swift b/HardcoreData/HardcoreData.swift index 048effa..542f8ae 100644 --- a/HardcoreData/HardcoreData.swift +++ b/HardcoreData/HardcoreData.swift @@ -70,48 +70,6 @@ public enum HardcoreData { } - /** - The HardcoreDataLogger instance to be used. The default logger is an instance of a DefaultLogger. - */ - public static var logger: HardcoreDataLogger = DefaultLogger() - - - // MARK: Internal - - internal static func log(level: LogLevel, message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { - - self.logger.log( - level: level, - message: message, - fileName: fileName, - lineNumber: - lineNumber, - functionName: - functionName - ) - } - - internal static func handleError(error: NSError, _ message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { - - self.logger.handleError( - error: error, - message: message, - fileName: fileName, - lineNumber: lineNumber, - functionName: functionName) - } - - internal static func assert(@autoclosure condition: () -> Bool, _ message: String, fileName: StaticString = __FILE__, lineNumber: Int = __LINE__, functionName: StaticString = __FUNCTION__) { - - self.logger.assert( - condition, - message: message, - fileName: fileName, - lineNumber: lineNumber, - functionName: functionName) - } - - // MARK: Private private static let defaultStackBarrierQueue = GCDQueue.createConcurrent("com.hardcoreData.defaultStackBarrierQueue") diff --git a/HardcoreData/NSManagedObject+Transaction.swift b/HardcoreData/NSManagedObject+Transaction.swift index ff0a131..bec78a6 100644 --- a/HardcoreData/NSManagedObject+Transaction.swift +++ b/HardcoreData/NSManagedObject+Transaction.swift @@ -59,25 +59,25 @@ internal extension NSManagedObject { let objectID = self.objectID if objectID.temporaryID { - var permanentIDError: NSError? - if !context.obtainPermanentIDsForObjects([self], error: &permanentIDError) { + var error: NSError? + if !context.obtainPermanentIDsForObjects([self], error: &error) { HardcoreData.handleError( - permanentIDError!, + error ?? NSError(hardcoreDataErrorCode: .UnknownError), "Failed to obtain permanent ID for object.") return nil } } - var existingObjectError: NSError? - if let existingObject = context.existingObjectWithID(objectID, error: &existingObjectError) { + var error: NSError? + if let existingObject = context.existingObjectWithID(objectID, error: &error) { return (existingObject as! T) } HardcoreData.handleError( - existingObjectError!, - "Failed to load existing NSManagedObject in context.") + error ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed to load existing \(T.self) in context.") return nil; } } \ No newline at end of file diff --git a/HardcoreData/NSManagedObjectContext+HardcoreData.swift b/HardcoreData/NSManagedObjectContext+HardcoreData.swift index 0d5acdb..1455c85 100644 --- a/HardcoreData/NSManagedObjectContext+HardcoreData.swift +++ b/HardcoreData/NSManagedObjectContext+HardcoreData.swift @@ -75,23 +75,21 @@ internal extension NSManagedObjectContext { let context = note.object as! NSManagedObjectContext let insertedObjects = context.insertedObjects - if insertedObjects.count <= 0 { + let numberOfInsertedObjects = insertedObjects.count + if numberOfInsertedObjects <= 0 { return } - var permanentIDError: NSError? - if context.obtainPermanentIDsForObjects(Array(insertedObjects), error: &permanentIDError) { + var error: NSError? + if context.obtainPermanentIDsForObjects(Array(insertedObjects), error: &error) { return } - if let error = permanentIDError { - - HardcoreData.handleError( - error, - "Failed to obtain permanent IDs for inserted objects.") - } + HardcoreData.handleError( + error ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed to obtain permanent ID(s) for \(numberOfInsertedObjects) inserted object(s).") }) } diff --git a/HardcoreData/NSManagedObjectContext+Querying.swift b/HardcoreData/NSManagedObjectContext+Querying.swift index d13b6b8..49c305c 100644 --- a/HardcoreData/NSManagedObjectContext+Querying.swift +++ b/HardcoreData/NSManagedObjectContext+Querying.swift @@ -58,7 +58,9 @@ public extension NSManagedObjectContext { } if fetchResults == nil { - HardcoreData.handleError(error!, "Failed executing fetch request.") + HardcoreData.handleError( + error ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed executing fetch request.") return nil } @@ -90,7 +92,9 @@ public extension NSManagedObjectContext { } if fetchResults == nil { - HardcoreData.handleError(error!, "Failed executing fetch request.") + HardcoreData.handleError( + error ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed executing fetch request.") return nil } @@ -120,7 +124,9 @@ public extension NSManagedObjectContext { } if count == NSNotFound { - HardcoreData.handleError(error!, "Failed executing fetch request.") + HardcoreData.handleError( + error ?? NSError(hardcoreDataErrorCode: .UnknownError), + "Failed executing fetch request.") return 0 } diff --git a/HardcoreData/NSManagedObjectContext+Transaction.swift b/HardcoreData/NSManagedObjectContext+Transaction.swift index 8a504d1..22dbba0 100644 --- a/HardcoreData/NSManagedObjectContext+Transaction.swift +++ b/HardcoreData/NSManagedObjectContext+Transaction.swift @@ -94,7 +94,7 @@ internal extension NSManagedObjectContext { HardcoreData.handleError( error, - "Failed to save NSManagedObjectContext.") + "Failed to save \(NSManagedObjectContext.self).") result = SaveResult(error) } else { @@ -153,7 +153,7 @@ internal extension NSManagedObjectContext { HardcoreData.handleError( error, - "Failed to save NSManagedObjectContext.") + "Failed to save \(NSManagedObjectContext.self).") if let completion = completion { GCDQueue.Main.async { diff --git a/HardcoreData/SortedBy.swift b/HardcoreData/SortedBy.swift index 07199f5..05bfe9f 100644 --- a/HardcoreData/SortedBy.swift +++ b/HardcoreData/SortedBy.swift @@ -100,7 +100,7 @@ public struct SortedBy: FetchClause { if fetchRequest.sortDescriptors != nil { - HardcoreData.log(.Warning, message: "Existing sortDescriptors for the NSFetchRequest was overwritten by SortedBy query clause.") + HardcoreData.log(.Warning, message: "Existing sortDescriptors for the \(NSFetchRequest.self) was overwritten by \(self.dynamicType) query clause.") } fetchRequest.sortDescriptors = self.sortDescriptors diff --git a/HardcoreData/Where.swift b/HardcoreData/Where.swift index c07f0fb..673da8b 100644 --- a/HardcoreData/Where.swift +++ b/HardcoreData/Where.swift @@ -89,7 +89,7 @@ public struct Where: FetchClause { if fetchRequest.predicate != nil { - HardcoreData.log(.Warning, message: "An existing predicate for the NSFetchRequest was overwritten by Where query clause.") + HardcoreData.log(.Warning, message: "An existing predicate for the \(NSFetchRequest.self) was overwritten by \(self.dynamicType) query clause.") } fetchRequest.predicate = self.predicate