ios - 将服务器数据保存到核心数据,在后台线程问题

标签 ios json swift multithreading core-data

我知道并发真的很头疼。我看了很多关于如何解析服务器数据并将其保存到核心数据的文章。但是很多教程都是非常基础的,它们不适用于线程。但是当我们开发应用程序时,需要多线程。

我的应用流程如下

1.使用URLSession从服务器获取数据
2.并解析
3.保存到核心数据-在后台,需要检查重复项 4.然后获取数据
5.更新界面。

我卡在第 3 步 保存到核心数据 - 在后台,需要检查重复项

我读到,URLSession 在后台线程中运行。是否需要像苹果所说的那样使用 performblock ? https://developer.apple.com/library/content/documentation/Cocoa/Conceptual/CoreData/Concurrency.html

我尝试了以下方式。但有时它会崩溃。如果有人建议正确的编程流程会更好。对此有很多问题,但对于这个问题没有正确的解决方案。

func DownloadFrom_server(dict:Any,urlstring_get:String)  {
    if JSONSerialization.isValidJSONObject(dict) {
        do{
            let json:Data = try JSONSerialization.data(withJSONObject: dict, options: JSONSerialization.WritingOptions.prettyPrinted)

            var urlString = urlstring_get
            urlString =   urlString.addingPercentEncoding(withAllowedCharacters: CharacterSet.urlPathAllowed)!
            var httpRequest = URLRequest(url: URL(string: urlString)!)
            httpRequest.httpMethod = "POST"
            httpRequest.httpBody = json
            let sessionConfig = URLSessionConfiguration.default
            sessionConfig.httpAdditionalHeaders = ["Accept" : "application/json", "api-key" : "API_KEY"]
            let session = URLSession(configuration: sessionConfig)
            let task = session.dataTask(with: httpRequest) { data, response, error in
                guard let data_get = data, error == nil else{// check for fundamental networking error
                    print("data nil\(error)")
                    //1.network connection lost
                    //save offline data
                    return
                }
                do {
                    let jsonResult = try JSONSerialization.jsonObject(with: data_get, options: JSONSerialization.ReadingOptions.mutableContainers)
                    print("cloud data",jsonResult)
                    self.Save_server_Data_ToCoreData(jsonResult: jsonResult)
                }
                catch {
                    print("json result parsing error ",error)
                }  
            }
            task.resume()
        }   
        catch{ 
            print("InValidJSONObject json:Data error - ",error)
        }
    }
}

并将服务器josn保存到核心数据如下

func Save_server_Data_ToCoreData(jsonResult:Any)  {
    let context = getContext()
    let privateMOC = NSManagedObjectContext(concurrencyType: .privateQueueConcurrencyType)
    privateMOC.parent = context
    privateMOC.perform {
        if let data = jsonResult  as? [[String: AnyObject]]{
            //Heree prepare MOC
            // if i need to check data alredy exits or not means how can i check
        }
        do {
            try privateMOC.save()
          context.performAndWait {
                do {
                    try context.save()
                } catch {
                    fatalError("Failure to save context: \(error)")
                }
            }
        } catch {
            fatalError("Failure to save context: \(error)")
        }
   }

   DispatchQueue.main.async(execute: {
                        print("update main")
                    })
}

我又想按照下面的方式做

             DispatchQueue.global(qos: .background).async {
//saving core data
 //fetching data
DispatchQueue.main.async {
   //update UI
}
     }

不确定需要使用哪个上下文,private 还是 main。如果有人回答这个问题,对像我这样的多线程初学者会有用。

最佳答案

对于核心数据中的口是心非检查。 ios9以上Coredata有一个特有的约束特性。

在实体描述的约束中设置属性名,如id、name等

enter image description here

并在 managedobjectcontext 中将合并策略设置为 NSMergeByPropertyObjectTrumpMergePolicy

managedObjectContext.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy

请记住,如果您在实体中有关系(我已在 xcode7.3 中检查过),上述口是心非检查功能将不起作用。

关于ios - 将服务器数据保存到核心数据,在后台线程问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41035845/

相关文章:

javascript - 我可以使用 LoDash 将大型 json 对象(来自 REST 服务)映射到较小的对象吗?

swift - SAP Fiori IOS SDK 离线 OData 过滤器问题

swift - RealityKit – 获取 ModelEntity 大小作为 SIMD3<Float>

ios - 如何通过在自定义 View 中按下按钮从 super View 中删除自定义 View ?

iphone - 我得到两个相同的 Root View

ios - 使用 Assets 目录时出现 AppCode 警告 "Resource not found"

java - JSONArray 在编码时丢失

PascalScript 中的 JSON 解析器

php - gif 文件从 php 到 iphone

ios - iOS-Swift。从MVC到MVVM重构。使用Delegate方法处理IBAction