7

の親子コンテキストについて少し混乱していManagedObjectContextます。

子コンテキストをセットアップして親コンテキストを設定すると、子コンテキストには親コンテキストのすべてのオブジェクトが含まれますか? で作成されるストックCore Dataメソッドを使用していますが、をメインAppDelegateに変更しました。ConcurrencyQueue

データベースを更新するはずの私の方法では:

  • 子コンテキストの作成、親コンテキストの設定
  • 子コンテキストでブロックを実行
  • 親コンテキストからフェッチ
  • 子コンテキストでオブジェクトを作成または更新する
  • 子コンテキストで保存を呼び出す
  • 子コンテキストの保存を処理する通知リスナーを用意する
  • 親コンテキストを保存

私の問題は、子コンテキストに何かを保存しているように見えないことです。Update または Create ChatMessage の println メッセージが表示されません。ここで何が間違っていますか?

AppDelegate コア データ メソッド

lazy var managedObjectContext: NSManagedObjectContext? = {
        // Returns the managed object context for the application (which is already bound to the persistent store coordinator for the application.) This property is optional since there are legitimate error conditions that could cause the creation of the context to fail.
        let coordinator = self.persistentStoreCoordinator
        if coordinator == nil {
            return nil
        }

        var managedObjectContext = NSManagedObjectContext(concurrencyType: .MainQueueConcurrencyType)
        managedObjectContext.persistentStoreCoordinator = coordinator
        managedObjectContext.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy

        NSNotificationCenter.defaultCenter().addObserver(self, selector: "contextDidSave:", name: NSManagedObjectContextDidSaveNotification, object: nil)

        return managedObjectContext
    }()

    func contextDidSave(notification: NSNotification) {
        let sender = notification.object as! NSManagedObjectContext
        if sender != managedObjectContext {
            managedObjectContext?.mergeChangesFromContextDidSaveNotification(notification)
            println("Core Data: merging changes from child context")
            saveContext()
        }
    }

更新を処理するデータベース クラス

lazy var parentContext: NSManagedObjectContext? = {
        if let managedObjectContext = self.appDelegate.managedObjectContext {
            return managedObjectContext
        }
        else {
            return nil
        }
        }()

func updateMessage(chatMessage: ChatMessage) {
        if chatMessage.id.isEmpty { return }

        let childContext = NSManagedObjectContext(concurrencyType: .PrivateQueueConcurrencyType)
        childContext.parentContext = parentContext
        childContext.performBlock({
            let objectIdDesc = NSExpressionDescription()
            objectIdDesc.name = "objectID"
            objectIdDesc.expression = NSExpression.expressionForEvaluatedObject()
            objectIdDesc.expressionResultType = NSAttributeType.ObjectIDAttributeType

            let fetchRequest = NSFetchRequest(entityName: "ChatMessage")
            fetchRequest.predicate = NSPredicate(format: "id == %@", chatMessage.id)
            fetchRequest.propertiesToFetch = [objectIdDesc]
            fetchRequest.resultType = .DictionaryResultType

            var error: NSError?
            if let results = self.parentContext!.executeFetchRequest(fetchRequest, error: &error) {
                if error == nil {
                    if !results.isEmpty {
                        if let objectId = results[0].valueForKey("objectID") as? NSManagedObjectID {
                            let fetched = childContext.objectWithID(objectId) as! ChatMessage
                            fetched.id = chatMessage.id
                            fetched.senderUserId = chatMessage.senderUserId
                            fetched.senderUsername = chatMessage.senderUsername
                            fetched.receiverUserId = chatMessage.receiverUserId
                            fetched.receiverUsername = chatMessage.receiverUsername
                            fetched.messageType = chatMessage.messageType
                            fetched.message = chatMessage.message
                            fetched.timestamp = chatMessage.timestamp
                            fetched.filepath = chatMessage.filepath
                            println("Updated ChatMessage: \(fetched.id)")
                        }
                        else {
                            var newMessage = NSEntityDescription.insertNewObjectForEntityForName("ChatMessage", inManagedObjectContext: childContext) as! ChatMessage
                            newMessage.id = chatMessage.id
                            newMessage.senderUserId = chatMessage.senderUserId
                            newMessage.senderUsername = chatMessage.senderUsername
                            newMessage.receiverUserId = chatMessage.receiverUserId
                            newMessage.receiverUsername = chatMessage.receiverUsername
                            newMessage.messageType = chatMessage.messageType
                            newMessage.message = chatMessage.message
                            newMessage.timestamp = chatMessage.timestamp
                            newMessage.filepath = chatMessage.filepath
                            println("Create ChatMessage: \(newMessage.id)")
                        }
                    }
                }
                else {
                    println("Fetch Message Object ID Error: \(error?.localizedDescription)")
                }
            }
        })
        childContext.save(nil)
    }
4

1 に答える 1