如何使JSON数据持久以供脱机使用(Swift 4)

DJF*_*iar 1 core-data swift

在我的应用程序中,我目前正在处理托管在网站上的JSON文件.我想这样做,以便如果用户打开应用程序并且没有数据连接,它将使用上次下载的数据.我不完全确定如何解决这个问题.

我最初的想法是下载JSON本身,然后简单地比较加载时的版本号,如果更新则下载它,然后编写应用程序以始终读取本地文件.但是,我想我只是看看网站,在本地存储JSON内容,然后在后续打开时,只需比较版本并更新其本地数据,如果网站上的版本更新.

一种方法优于另一种方法有什么优势吗?

我应该从哪里开始寻找有关制作数据的信息,我从网站托管的JSON加载本地和持久存储?我认为CoreData最适合这个,但我的Google-fu并没有发现如何将JSON带入Core Data.

编辑: Per Starksy的建议,我在我的应用程序中添加了以下内容,但我收到了错误let jsonData = try ....

func saveJSONFile() {
    let itemName = "myJSONFromWeb"
    let hostedJSONFile = "http://tourofhonor.com/BonusData.json"
    do {
        let directory = try FileManager.default.url(for: .documentDirectory, in: .userDomainMask, appropriateFor:nil, create:false)
        let fileURL = directory.appendingPathComponent(itemName)
        // let jsonData = try JSONDecoder().decode(hostedJSONFile.self, from: Data)
        let jsonData = try JSONSerialization.jsonObject(with: hostedJSONFile, options: .mutableContainers)
        try jsonData.write(to: fileURL, options: .atomic)
        //Save the location of your JSON file to UserDefaults
        defaults.set(fileURL, forKey: "pathForJSON")
    } catch {
        print(error)
    }
}
Run Code Online (Sandbox Code Playgroud)

错误是

对成员'jsonObject(with:options :)'的模糊引用

当我谷歌那个,我看到另一个SO帖子说我应该使用,JSONDecoder().decode因为我使用Swift 4,但我不知道如何转换上面的代码来使用该方法.

Sta*_*sky 5

如果您需要本地存储,我建议您查看Realm.它是Core Data的替代品,但更易于使用:https: //realm.io/docs/swift/latest/

具体来说,对于此任务,我不会保存到CoreData或Realm,而是直接保存到app目录,并将文件的版本和位置保存在UserDefaults中.

1)(更新的答案)

//Download the file from web and save it to the local directory on the device
let hostedJSONFile = "http://tourofhonor.com/BonusData.json"
let jsonURL = URL(string: hostedJSONFile)
let defaults = UserDefaults.standard
let itemName = "myJSONFromWeb"
do {
    let directory = try FileManager.default.url(for: .documentDirectory, in: .userDomainMask, appropriateFor: nil, create: false)
    let fileURL = directory.appendingPathComponent(itemName)
    let jsonData = try Data(contentsOf: jsonURL!)
    try jsonData.write(to: fileURL, options: .atomic)
    //Save the location of your JSON file to UserDefaults
    defaults.set(fileURL, forKey: "pathForJSON")
} catch {
    print(error)
}
Run Code Online (Sandbox Code Playgroud)

2)将您的JSON版本(如果它有来自Web的版本)保存到UserDefaults:

defaults.set(1, forKey: "jsonVersion")
Run Code Online (Sandbox Code Playgroud)

3)启动应用程序时,您需要将当前jsonVersion验证为您在文档目录中保存的版本:

let currentVersion = //...get the current version from your JSON file from web.
let existingVersion = defaults.integer(forKey: "jsonVersion")
if currentVersion != existingVersion {
   //Download the newest JSON and save it again to documents directory for future use. Also, use it now for your needs.
} else {
   //Retrieve the existing JSON from documents directory
   let fileUrl = defaults.url(forKey: "pathForJSON")
   do {
       let jsonData2 = try Data(contentsOf: fileUrl!, options: [])
       let myJson = try JSONSerialization.jsonObject(with: jsonData2, options: .mutableContainers)
       //...do thing with you JSON file
       print("My JSON: ", myJson)
   } catch {
       print(error)
   }
Run Code Online (Sandbox Code Playgroud)

  • 如果我的回答对您有帮助,请多多关照并给予肯定。谢谢 (2认同)