Url correct but the dictionary is null - ios

I have to download data using JSON, the url is correct (tested on chrome) but I get an empty dictionary. Where did I go wrong?
NSLog(#"'url is %#", stringUrl); //correct
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:stringUrl]];
NSHTTPURLResponse __autoreleasing *response = nil;
NSError __autoreleasing *error = nil;
NSData *result = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
// the result is:
/* <280d0a0d 0a0d0a0d 0a0d0a0d 0a0d0a7b 22636f6d 6d6f6e22 3a7b2261 636b223a
224f4b22 2c226661 756c7443 6f646522 3a6e756c 6c2c2266 61756c74 53747269
6e67223a 6e756c6c 7d2c2274 6f74616c 223a3138 362c2270 61676522 3a312c22
.......*/
NSString *str = [[NSString alloc] initWithData:result encoding:NSUTF8StringEncoding];
NSLog(#" STRING IS %#", str);
//the string is correct
SBJsonParser *parser = [[SBJsonParser alloc] init];
NSLog (#"The parser is %#", parser);
//The parser is <SBJsonParser: 0x8877400>
NSDictionary *object = [parser objectWithData: result];
NSLog(#" The dictionary is %#", object);// The dictionary is null
The result of string:
NSString *str = [[NSString alloc] initWithData:result encoding:NSUTF8StringEncoding];
NSLog(#" THE STRING IS %#", str);
/* ({"common":
{"ack":"OK",
"faultCode":null,
"faultString":null},
"total":8,
"page":1,
"limit":15,
"products":[{"name":"BANANE SOLIDAL BIOLOGICAL - cartone/estero/2^
cat.",
"code":"52436",
"anabel":"264342000",
"hasPezzature":true,
"pezzatureList":
[{"weight":700.000,"unit":"Gr","formatted":"700GR"}],
"disponible":true,
"promotionImage":null},
{"name":"KIWI IT 105-120 II^ VAS
500GR",
"code":"52094",
"anabel":"393261000",
"hasPezzature":true,
"pezzatureList":
[{"weight":500.000,"unit":"GR","formatted":"500GR"}],
"disponible":true,
"promotionImage":null},
........
.........]});*/
I put the formatting so to be readable, in fact the returned data is all on one line

There is a "(" and ")" at the starting and ending of the JSON response when you try to cast it in a NSDictionary or NSArray, it doesnt recognize it and hence goes empty. So to get it parsed you'll need to add this:
str = [[str stringByReplacingOccurrencesOfString:#"(" withString:#""] stringByReplacingOccurrencesOfString:#")" withString:#""];
before
SBJsonParser *parser = [[SBJsonParser alloc] init];
NSLog (#"The parser is %#", parser);
//The parser is <SBJsonParser: 0x8877400>
NSDictionary *object = [parser objectWithData: result];
NSLog(#" The dictionary is %#", object);// The dictionary is null

Related

Exception Error while loading data from response in Custom Table View Controller in IOS

Made a custom table view controller in which call a service in viewDidLoad method. The service is called with some parameters and it is GET request. The response is coming fine but it is showing an exception error this,Terminating app due to uncaught exception
'NSUnknownKeyException', reason: '[<__NSCFString 0x60000036a140> valueForUndefinedKey:]: this class is not key value coding-compliant for the key data.'
My response from service is this
{"data":[{"id":"139559","first_name":"Shoaib Anwar","last_name":null,"address":null,"mobile":"03233008757","city":null,"date":"2017-08-10","date_of_birth":"1992-08-10"}]}.
The app crashes all the time , i'm confused why it is showing this error.
My code is this,
NSString *savedValue = [[NSUserDefaults standardUserDefaults]
stringForKey:#"number"];
NSString *url=#"My Url";
NSString *string3 = [url stringByAppendingString:savedValue];
NSString *lastArray = #"&type=json";
string3 = [string3 stringByAppendingString:lastArray];
NSLog(#"Mmm %#",savedValue);
NSLog(#"Mmm %#",string3);
NSString *targetUrl = [NSString stringWithFormat:#"%#",string3];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setHTTPMethod:#"GET"];
[request setURL:[NSURL URLWithString:targetUrl]];
[[[NSURLSession sharedSession] dataTaskWithRequest:request completionHandler:
^(NSData * _Nullable data,
NSURLResponse * _Nullable response,
NSError * _Nullable error) {
NSString *myString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSLog(#"Data received: %#", myString);
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data
options:NSJSONReadingMutableContainers
error:nil];
NSString *value = json[#"data"];
_Ids = [NSMutableArray array];
for (NSDictionary * oneCustomer in value)
{
// Create a new Customer record
ViewProfile * newCustomer = [[ViewProfile alloc] init];
newCustomer.ids = [oneCustomer objectForKey:#"id"];
NSLog(#"ID: %# ", newCustomer.ids);
newCustomer.fname = [oneCustomer objectForKey:#"first_name"];
NSLog(#"Fname: %# ", newCustomer.fname);
newCustomer.lname = [oneCustomer objectForKey:#"last_name"];
NSLog(#"Lname: %# ", newCustomer.lname);
newCustomer.address = [oneCustomer objectForKey:#"address"];
NSLog(#"Address: %# ", newCustomer.address);
newCustomer.mobile = [oneCustomer objectForKey:#"mobile"];
NSLog(#"Mobile: %# ", newCustomer.mobile);
newCustomer.city = [oneCustomer objectForKey:#"city"];
NSLog(#"City: %# ", newCustomer.city);
newCustomer.date = [oneCustomer objectForKey:#"date"];
NSLog(#"Date: %# ", newCustomer.date);
newCustomer.dob = [oneCustomer objectForKey:#"date_of_birth"];
NSLog(#"DOB: %# ", newCustomer.dob);
// Add our new Customer record to our NSMutableArray
[_Ids addObject:newCustomer];
}
dispatch_async(dispatch_get_main_queue(), ^{
// This code will run once the JSON-loading section above has completed.
[self.tableView reloadData];
});
NSString *status=[myString valueForKey:#"data"];
NSLog(#"Status:%#",status);
}] resume];
Your response is a json string.
Try to convert myString property to NSData type and then pass to NSJsonSerialisation class.
NSData *jsonData = [myString dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingMutableContainers error:nil];
Hope this helps :)
you should comment this line
NSString *status=[myString valueForKey:#"data"];
or check your storyboard or Xib
are you have Label or Button like the image attached
Please try below code and update according to your requirement.
NSString *myString = #"{\"data\":[{\"id\":\"139559\",\"first_name\":\"Shoaib Anwar\",\"last_name\":null,\"address\":null,\"mobile\":\"03233008757\",\"city\":null,\"date\":\"2017-08-10\",\"date_of_birth\":\"1992-08-10\"}]}";
NSData *data = [myString dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
NSArray *value = json[#"data"];
for (NSDictionary * oneCustomer in value)
{
// Create a new Customer record
NSLog(#"ID: %# ", [oneCustomer objectForKey:#"id"]);
NSLog(#"Fname: %# ", [oneCustomer objectForKey:#"first_name"]);
}
Crashing issue because of NSString *status=[myString valueForKey:#"data"];

Deserialise JSON String in Objective C

I received NSData object data from REST API. That contains JSON data which I want to parse.
{
JsonResult = "[{
\"IsAuth\":\"true\",
\"User\":\"
[
{
\\\"userid\\\":\\\"josephH\\\",
\\\"firstname\\\":\\\"joseph\\\",
\\\"lastname\\\":\\\"Henry\\\",
}
]\"}]"
}
This statement gave me the result as a String like below which I am not able to parse as JSON.
myData = [data valueForKey:#"JsonResult"];
"[{
\"IsAuth\":\"true\",
\"User\":\"
[
{
\\\"userid\\\":\\\"josephH\\\",
\\\"firstname\\\":\\\"joseph\\\",
\\\"lastname\\\":\\\"Henry\\\",
}
]\"}]"
When I try to pass this mydata to JSONSerialization the code crashes.
How do I cast the above string to NSDictionary so that I can parse them and use the values of IsAuth and User.?
Code:
[LDService authenticateUser:Uname.text passwordString:Password.text completeBlock:^(NSData * data){
NSError *error;
NSData *jsonData;
NSString *jsonString = nil;
NSMutableDictionary *jsonDict;
if([NSJSONSerialization isValidJSONObject:data])
{
jsonData = [NSJSONSerialization dataWithJSONObject:data
options:kNilOptions
error:&error];
jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}
NSString *formattedString = [jsonString stringByReplacingOccurrencesOfString:#"\\\"" withString:#"'"];
NSLog(#"Formatted string %#",formattedString);
[jsonDict setObject:formattedString forKey:#"JsonResult"];
NSLog(#"Parsed json %#",jsonDict);
}];
Pass your data as data
NSError *error;
NSString *jsonString = nil;
if([NSJSONSerialization isValidJSONObject:data])
{
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:data
options:kNilOptions
error:&error];
jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}
then replace occurance of #"\\\" with #"'"
NSString *formattedString = [jsonString stringByReplacingOccurrencesOfString:#"\\\"" withString:#"'"];
then use this formattedString.
I have investigates your json file from Json formatter & Validator, there are lots of error in your json file, so first check your file from this validator and this formatter gives you error with description. Re-build your json file, if you still getting any problem then ask.

iOS is creating a JSON String without {} -- only has [ ]?

Why is the assignment to jsonString not including braces{}?
Here's what I'm getting:
["anemail#chdr.com"]
CODE
if (_allEmails)
{
NSError *error = nil;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:_allEmails options:0 error:&error];
if (!error)
{
NSString *jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
[dictionary setObject:jsonString forKey:#"AllEmails"];
}
}
The _allEmails variable must be an array (you tell me) and for braces you need to store your data in a dictionary.
Perhaps what you're looking for is:
if ([_allEmails count] > 0)
{
NSError *error = nil;
NSDictionary *dict = #{ #"AllEmails" : _allEmails };
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dict
options:0
error:&error];
// Note: Check returned object and not NSError object
if (jsonData) {
NSString *jsonString = [[NSString alloc] initWithData:jsonData
encoding:NSUTF8StringEncoding];
// Do thing with string
} else {
NSLog(#"Failed to serialize JSON: %#", [error localizedDescription]);
}
}
Because a JSON array is not enclosed braces, and what you have above is a JSON array. A JSON "object" is enclosed in braces.

Parse JSON using NSURLConnection

I am using Bing Search API and able to successfully parse the xml but not JSON.Below is the code to both parse xml and JSON,when I nslog the output of the JSON it shows "null" I don't know how to proceed from here.
-(void)searchBing:(NSString *)text{
//NSString *query1 = #"San Francisco Baseball";
NSString *query = [NSString stringWithFormat: #"'%#'",text];
//NSString *query = query1;
NSString *format = #"atom";
NSString *market = #"'en-us'";
//NSInteger top = 2;
NSMutableString *fullURL = [NSMutableString stringWithCapacity:256];
[fullURL appendString:URL];
[fullURL appendFormat:#"Web?$format=%#", format];
[fullURL appendFormat:#"&Query=%#",
[query stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]];
[fullURL appendFormat:#"&Market=%#",
[market stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]];
// [fullURL appendFormat:#"&$top=%d", top];
NSURLConnection *connection = [[NSURLConnection alloc] initWithRequest:
[self getRequest:fullURL] delegate:self];
if (connection)
{
NSLog(#"Connection established");
}
else
{
NSLog(#"Connection failed");
}
}
Below where am parsing both xml(successful) and JSON(unsuccessful)
- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
// The request is complete and data has been received
// You can parse the stuff in your instance variable now
// convert to JSON
NSLog(#"Finished loading: Received %d bytes of data",[self.responseData length]);
NSXMLParser *parser = [[NSXMLParser alloc] initWithData: self.responseData];
[parser setDelegate: self];
[parser parse];
NSLog(#"XMl == %#",parser);
NSError *myError = nil;
NSDictionary *res = [NSJSONSerialization JSONObjectWithData:self.responseData options:kNilOptions error:&myError];
NSLog(#"json data = %#",res);//getting null
}
Am using Base_64 encoding and to all viewers nothing wrong with query because getting correct information via xml parser.But I want response in JSON.
Structure sample
{
"SearchResponse":{
"Version":"2.2",
"Query":{
"SearchTerms":"testign"
},
"Spell":{
"Total":1,
"Results":[
{
"Value":"testing"
}
]
},
"Web":{
"Total":5100,
"Offset":0,
"Results":[
{
"Title":"Testign part 2 - Tiernan OTooles Programming Blog",
"Description":"If this works, it means nothing really, but i have managed to build a .TEXT blog posting app. could be handy if i move my main blog to .TEXT, which i am thinking about..",
"Url":"http:\/\/weblogs.asp.net\/tiernanotoole\/archive\/2004\/09\/24\/233830.aspx",
"DisplayUrl":"http:\/\/weblogs.asp.net\/tiernanotoole\/archive\/2004\/09\/24\/233830.aspx",
"DateTime":"2008-10-21T05:08:05Z"
}
]
}
}
}
From your post:
NSXMLParser *parser = [[NSXMLParser alloc] initWithData: self.responseData];
.
.
.
NSDictionary *res = [NSJSONSerialization JSONObjectWithData:self.responseData options:kNilOptions error:&myError];
It looks like you're trying to use the same data as XML and JSON. You can't do that. The data returned from the server is in one form OR the other. It won't be both.

JSON iOS parsing string

{"response":[33689822,64091979,69682048,74160161]}
-
- (void)requestCompleted:(ASIHTTPRequest *)request
{
NSString *responseString = [request responseString];
NSLog(#"okRequest|| %#",responseString);
SBJSON *parser = [[SBJSON alloc] init];
// Prepare URL request to download statuses from Twitter
// Get JSON as a NSString from NSData response
NSString *json_string = [[NSString alloc] initWithString:responseString];
// parse the JSON response into an object
// Here we're using NSArray since we're parsing an array of JSON status objects
NSArray *statuses = [parser objectWithString:json_string error:nil];
// Each element in statuses is a single status
// represented as a NSDictionary
for (NSDictionary *status in statuses)
{
//all other func..
NSLog(#"%# ", status);///This func prints only "response"
}
}
How I can get array of numbers in "response"? (33689822,64091979,69682048,74160161)
Try this:
for (NSNumber *number in [statuses objectForKey:#"response"]) {
NSLog(#"%#", number);
}
You can either parse the JSON data yourself, or better, use a library like TouchJSON to do it for you.
Try using JSONFragmentValue directly.
NSString *response=[request responseString];
id usableResp = [response JSONFragmentValue];

Resources