Reputation: 1278
I am aware that there are many similar SO questions that have a similar title to mine. I have checked them out and am still running into this problem.
I am trying to access an API that returns a string that should/could be formatted as JSON.
To retrieve this string as convert the string to JSON I'm using (unsuccessfully) this code:
NSError *error;
NSURLRequest *request = [NSURLRequest requestWithURL:url];
NSURLSession *session = [NSURLSession sharedSession];
NSURLSessionDataTask *task = [session dataTaskWithRequest:request
completionHandler:
^(NSData *data, NSURLResponse *response, NSError *error) {
NSString *responseString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSLog(@"Response: %@",responseString);
NSData *jsonData = [responseString dataUsingEncoding:NSUTF8StringEncoding];
id json = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:nil];
NSLog(@"%@",[json objectForKey:@"ID"]);
NSLog(@"Json: %@",json);
}];
[task resume];
The NSLog(@"Response:...) returns a string that when I enter it into this website: http://jsonviewer.stack.hu confirms that the string is valid JSON.
Both NSLog's that are supposed to return a JSON value come back null.
What iv'e tried:
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingMutableContainers error:&error];
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:&error];
I have also now tried:
NSURLRequest *request = [NSURLRequest requestWithURL:url];
NSURLSession *session = [NSURLSession sharedSession];
NSURLSessionDataTask *task = [session dataTaskWithRequest:request
completionHandler:
^(NSData *data, NSURLResponse *response, NSError *error) {
NSMutableDictionary *jsonObject;
NSError *err = nil;
@try
{
jsonObject = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:&err];
}
@catch (NSException *exception)
{
NSLog( @"Exception caught %@",exception);
}
NSDictionary *info = jsonObject;
NSLog(@"Json: %@",info);
}];
[task resume];
What am I doing wrong here? How can I get a NSDictionary (JSON) result.
Upvotes: 0
Views: 950
Reputation: 26096
Your main issue:
If you read the error parameter of +JSONObjectWithData:options:error:
, it will tell you this:
Error Domain=NSCocoaErrorDomain Code=3840 "JSON text did not start with array or object and option to allow fragments not set." UserInfo={NSDebugDescription=JSON text did not start with array or object and option to allow fragments not set.}
As stated, your answer looks like this: aStringKey = realAndValidJSONSurroundedByCurvyBrackets
, which is not a valid JSON.
After discussion in chat, you have contact with the server side, and it should be their responsibility to give proper JSON. Until they fix it, in order to keep working, you can do:
NSString *str = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
str = [str stringByReplacingCharactersInRange:NSMakeRange(0, [@"aStringKey = " length] ) withString:@""];
NSError *jsonError = nil;
NSDictionary *jsonFinal = [NSJSONSerialization JSONObjectWithData:[str dataUsingEncoding:NSUTF8StringEncoding] options:0 error:&jsonError];
if (jsonError)
{
NSLog(@"Error: %@", jsonError);
}
But remember, that's a "quick hack/fix" and shouldn't be left in final version and remove as soon as possible.
You tried:
NSError *err = nil;
@try
{
jsonObject = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:&err];
}
@catch (NSException *exception)
{
NSLog( @"Exception caught %@",exception);
}
The @try{}@catch(NSException *exception)
shouldn't work since +JSONObjectWithData:options:error:
shouldn't throw a NSException
in your case, so in theory, there is nothing to catch, and but it may still not work (since there is a NSError
).
Of course, since data
parameter should be non null, if it's nil
, you'll get a NSException
(which would log Exception caught data parameter is nil
), but that's another issue and doesn't assure you that the parsing went wrong (because of invalid JSON like in our case) if there is no exception.
Upvotes: 2
Reputation: 751
Try this:
NSMutableDictionary *jsonObject;
NSError *err = nil;
@try
{
jsonObject = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:&err];
}
@catch (NSException *exception)
{
NSLog( @"Exception caught %@",exception);
}
NSDictionary *info = jsonObject;
Upvotes: 1