Radu Tataru
Radu Tataru

Reputation: 49

Read JSON data from file Swift 2.0 works on simulator but not on device, return json null

Hello I'm trying to write and read some data JSON format from file in my app. I know that on device filename is key sensitive and i checked it twice. My problem is to understand why it works fine on simulator and return null JSON data on device.Thank you a lot!

func writeJsonData() {

    let file = "/settings.json"
    if let dir :  NSString = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.AllDomainsMask, true).first {
        let path = dir.stringByAppendingPathComponent(file);
            let json =  ["val1":1, "val2":2]
            self.jsonToNSData(json)
            if let file = NSFileHandle(forWritingAtPath:path) {
                file.writeData(jsonToNSData(json)!)
        }
    }

    self.readJsonData()
}

func readJsonData () {

    let file = "/settings.json"
    if let dir :  NSString = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.AllDomainsMask, true).first {
        let path = dir.stringByAppendingPathComponent(file);
        if let data = NSData(contentsOfFile: path as String) {
            let json = JSON(data: data)
            print(json)  // !!!!!!!!!!!
            if json != JSON.null {

                let val1 = json["val1"].int!
                let val2 = json["val2"].int!
            }
        }
    }
}

the problem is in writing data, the corect way is:

func writeJsonData() {
        let file = "file.json"
        if let dir :  NSString = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.AllDomainsMask, true).first {
            let path = dir.stringByAppendingPathComponent(file);
                let json: JSON =  ["val1":val1 as Int, "val2":val2 as Int]
                let str = json.description
                let data = str.dataUsingEncoding(NSUTF8StringEncoding)!
                if let file = NSFileHandle(forWritingAtPath:path) {
                    file.writeData(data)
            }
        }
   }

Upvotes: 0

Views: 1719

Answers (1)

Jeef
Jeef

Reputation: 27275

let file = "/settings.json" is not going to work on the device.

You need to look at NSBundle (i'll update this post in a min or two when I can pull you some sample code)

I only have objective c code at the moment - but it should be the same:

NSBundle* myBundle = [NSBundle bundleWithIdentifier:@"org.mitre.EGM96GeoidCalculator"];
NSString *path2 = [myBundle pathForResource:@"EGM96" ofType:@""];

What you need to do in swift - etc is similar (see this post: Reading in a JSON File Using Swift)

if let path = NSBundle.mainBundle().pathForResource("test", ofType: "json")
{
    if let jsonData = NSData(contentsOfFile: path, options: .DataReadingMappedIfSafe, error: nil)
    {
        if let jsonResult: NSDictionary = NSJSONSerialization.JSONObjectWithData(jsonData, options: NSJSONReadingOptions.MutableContainers, error: nil) as? NSDictionary
        {
            if let persons : NSArray = jsonResult["person"] as? NSArray
            {
                // Do stuff
            }
        }
     }
}

Now if you are doing something in a framework - or what not you don't want to access mainBundle but rather the bundle with the identifier of the framework.

Upvotes: 1

Related Questions