iOS-error in parsing the data - ios

In my app, I am parsing the data using JSON
NSString * urlString=[NSString stringWithFormat:#"http://userRequest?userid=bala#gmail.com&latitude=59.34324&longitude=23.359257"];
NSURL * url=[NSURL URLWithString:urlString];
NSMutableURLRequest * request=[NSMutableURLRequest requestWithURL:url];
NSError * error;
NSURLResponse * response;
NSData *data=[NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
NSString * outputData=[[NSString alloc]initWithData:data encoding:NSASCIIStringEncoding];
NSLog(#"%#",outputData);
SBJsonParser *jsonParser = [SBJsonParser new];
NSDictionary *jsonData = (NSDictionary *) [jsonParser objectWithString:outputData error:nil];
NSLog(#"%#",jsonData);
NSInteger success = [(NSNumber *) [jsonData objectForKey:#"success"] integerValue];
After this code executes, In my log it is printed as
({
latitude = "0.000000000000000";
longitude = "0.000000000000000";
username = sunil;
},
{
latitude = "80.000000000000000";
longitude = "30.000000000000000";
username = arun;
})
But while running, the app crashes, as
'NSInvalidArgumentException', reason: '-[__NSArrayM objectForKey:]: unrecognized selector sent to instance 0x910d8d0'

I think your problem is, that jsonParser objectWithString returns an array with dictionaries in it not dictionaries itself.
Try the following:
NSArray *jsonData = (NSArray *) [jsonParser objectWithString:outputData error:nil];
for(NSDictionary *dict in jsonData) {
NSLog(#"%#",dict);
}
Does that work for you ?

Your reponse is NSArray which contains NSDictionary. So frst get dictionary from array then access value. Also Your json not look like correct.
for (NSDictionary *dict in responseArray) {
double latitude = [dict[#"latitude"]doubleValue];
double longitude = [dict[#"latitude"] longitude];
NSString* name = dict[#"username"];
}

1. First of all you are getting NSArray in JSON
JSON Starts with "(" means NSArray
JSON Starts with "{" means NSDictionary
Here you are getting NSArray which has collection of NSDictionary,
{
latitude = "0.000000000000000";
longitude = "0.000000000000000";
username = sunil;
},...
2."success" key is not present in the JSON..
Fix
NSArray *jsonData = (NSArray *) [jsonParser objectWithString:outputData error:nil];
If([jsonData count]>0){
// Has some data
// Iterate NSDictionary and get data here
}
else{
// No Data
}

some where you are getting data from nsarray with using some object key. that key is invalid to fetching data from array

Related

Objective C JSON parse from NSMutableArray

I have a JSON like below (getting from an URL)-
{
action :getAllJournal;
data :{
journalList :[{
cancelled : F;
"cust_code" : "700-T022";
"journal_amount" : 2216;
"journal_code" : "JV1603/001";
"journal_date" : "2016-03-15 00:00:00";
"journal_id" : 1;
outstanding : 0;
},
{
cancelled : F;
"cust_code" : "700-0380";
"journal_amount" : 120;
"journal_code" : "JV1605/006";
"journal_date" : "2016-05-31 00:00:00";
"journal_id" : 2;
outstanding : 120;
},
{
cancelled : F;
"cust_code" : "700-T280";
"journal_amount" : 57;
"journal_code" : "JV1609/001";
"journal_date" : "2016-09-22 00:00:00";
"journal_id" : 3;
outstanding : 0;
}
];
};
message = "";
"message_code" = "";
result = 1;}
The code below doing is getting the JSON from URL and storing them in NSMutableArray. Until storing them into array, it's working fine but I'm bit confused with the JSON format and don't know how to get result by a key.
__block NSMutableArray *jsonArray = nil;
[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
NSString *urlString = [NSString stringWithFormat:#"http://xxxxxxx/api.php?action=getAllJournal"];
NSURLRequest * request = [NSURLRequest requestWithURL:[NSURL URLWithString:urlString]];
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError)
{
if (data)
{
id myJSON;
#try {
myJSON = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
}
#catch (NSException *exception) {
}
#finally {
}
jsonArray = (NSMutableArray *)myJSON;
NSString *nsstring = [jsonArray description];
NSLog(#"IN STRING -> %#",nsstring);
NSData *data = [nsstring dataUsingEncoding:NSUTF8StringEncoding];
NSError *jsonError;
NSDictionary *jsonObject = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&jsonError];
if(jsonObject !=nil){
if(![[jsonObject objectForKey:#"journalList"] isEqual:#""]){
NSMutableArray *array=[jsonObject objectForKey:#"journalList"];
NSLog(#"array: %lu",(unsigned long)array.count);
int k = 0;
for(int z = 0; z<array.count;z++){
NSString *strfd = [NSString stringWithFormat:#"%d",k];
NSDictionary *dicr = jsonObject[#"journalList"][strfd];
k=k+1;
// NSLog(#"dicr: %#",dicr);
NSLog(#"cust_code - journal_amount : %# - %#",
[NSMutableString stringWithFormat:#"%#",[dicr objectForKey:#"cust_code"]],
[NSMutableString stringWithFormat:#"%#",[dicr objectForKey:#"journal_amount"]]);
}
}
}else{
NSLog(#"Error - %#",jsonError);
}
}
}];
From this, I am able to get the JSON successfully. But it's always giving me this error: Error Domain=NSCocoaErrorDomain Code=3840 "No string key for value in an object around character 6." UserInfo={NSDebugDescription=No string key for value in an object around character 6.} How can I get all values from journalList? I'm new to iOS, that's why not sure what I'm missing.
id myJSON;
#try {
myJSON = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
}
#catch (NSException *exception) {
}
#finally {
}
jsonArray = (NSMutableArray *)myJSON;
NSString *nsstring = [jsonArray description];
NSLog(#"IN STRING -> %#",nsstring);
NSData *data = [nsstring dataUsingEncoding:NSUTF8StringEncoding];
NSError *jsonError;
NSDictionary *jsonObject = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&jsonError];
I'd say: NO and NO.
I wouldn't do a #try/#catch on a NSJSONSerialization, because the real issues are on the error parameter (and they won't throw a NSException for most of the cases). Just check if (data) is quite efficient.
Then, let's say it worked, and you have myJSON.
In fact, myJSON is a NSDictionary, not a NSArray, so the cast is useless and doesn't make sense.
Next issue:
Your are using -description (okay, if you want to debug), but you CAN'T use it to reconstruct AGAIN a JSON. It's not a valid JSON, it's the way the compiler "print" an object, it adds ";", etc.
If your print [nsstring dataUsingEncoding:NSUTF8StringEncoding] and data you'll see that they aren't the same.
For a more readable:
NSString *dataJSONStr = [[NSString alloc] initWithData:data encoding: NSUTF8StringEncoding];, it's clearly not the same structure as your nsstring.
Then, you are redoing the JSON serialization? Why ?
So:
NSError *errorJSON = nil;
NSDictionary *myJSON = [NSJSONSerialization JSONObjectWithData:data options:0 error:&errorJSON];
if (errorJSON)
{
NSLog(#"Oops error JSON: %#", errorJSON);
}
NSDictionary *data = myJSON[#"data"];
NSArray *journalList = data[#"journalList"]
for (NSDictionary *aJournalDict in journalList)
{
NSUInteger amount = [aJournalDict[#"journal_amount"] integerValue];
NSString *code = aJournalDict[#"journal_code"];
}
There is a dictionary named "data" you're not fetching, represented by {}.
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&jsonError];
if (!jsonError) {
// Fetch the journalList
NSArray *journalList = json[#"data"][#"journalList"];
// iterate over every entry and output the wanted values
for (NSDictionary *journal in journalList) {
NSLog(#"%# %#", journal[#"cust_code"], journal[#"journal_amount"]);
}
}
json[#"key"] is a short form of [json objectForKey:#"key"] I find easier to read.
That is not a valid JSON. Entries should be separated by comma ,, not semicolon ;
You need to fetch journalList from data.
Try below code:
This is demo code to create array like you:
NSMutableDictionary *jsonObject = [NSMutableDictionary new];
jsonObject[#"action"]= #"";
jsonObject[#"message"]= #"";
jsonObject[#"message_code"]= #"";
jsonObject[#"result"]= #"1";
NSMutableArray *ary1 = [NSMutableArray new];
for(int i=0;i<5;i++)
{
NSMutableDictionary *dd = [NSMutableDictionary new];
dd[#"cancelled"]= #"F";
dd[#"cust_code"]= #"F";
[ary1 addObject:dd];
}
NSMutableDictionary *dicjournal = [NSMutableDictionary new];
[dicjournal setObject:ary1 forKey:#"journalList"];
[jsonObject setObject:dicjournal forKey:#"data"];
This is main Logic:
NSMutableArray *journalList = [NSMutableArray new];
NSMutableDictionary *dic = [jsonObject valueForKey:#"data"];
journalList = [[dic objectForKey:#"journalList"] mutableCopy];
Looks like your JSON is invalid. You can see whether your JSON is correct or not using http://jsonviewer.stack.hu/ and moreover format it. Meanwhile your code is not using "data" key to fetch "journalList" array.
Code : -
NSDictionary *dic = [jsonObject valueForKey:#"data"];
NSMutableArray *arr = [dic objectForKey:#"journalList"];
for (int index=0 ; index < arr.count ; index++){
NSDictionary *obj = [arr objectAtIndex:index];
// Now use object for key from this obj to get particular key
}
Thanks #Larme and #Amset for the help. I was doing wrong the in the NSMutableArray part. The correct version of this code is in the below:
[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
NSString *urlString = [NSString stringWithFormat:#"http://xxxxxxx/api.php?action=getAllJournal"];
NSURLRequest * request = [NSURLRequest requestWithURL:[NSURL URLWithString:urlString]];
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError)
{
if (data)
{
id myJSON;
#try {
myJSON = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
}
#catch (NSException *exception) {
}
#finally {
}
NSArray *journalList = myJSON[#"data"][#"journalList"];
for (NSDictionary *journal in journalList) {
NSLog(#"%# %#", journal[#"journal_date"], journal[#"journal_amount"]);
}
}
}];

How to get particular object values and key values from JSON response?

I need to get Particular Object values ( A, B, C, D) and related key values (#"name" ). Here below I have posted my sample code and response. Please help me.
NSString *combined = URL;
NSURL *url = [[NSURL alloc] initWithString:combined];
NSData *responseData=[NSData dataWithContentsOfURL:url];
NSError *error;
NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:responseData options:kNilOptions error:&error];
NSArray *responsData = [jsonDictionary objectForKey:#"response"];
// GET A,B,C Object values
NSDictionary *d1 = responsData.firstObject;
NSEnumerator *enum1 = d1.keyEnumerator;
NSArray *firstObject = [enum1 allObjects];
My JSON Response :
response : [ {
A = [ {
name : tango
}
{
name : ping
}
]
B = [ {
name : tango
}
{
name : ping
}
]
} ]
You can achieve the list of all names using this:
NSMutableArray *names = [[NSMutableArray alloc] init];
for (NSDictionary *dict in responsData) {
[dict enumerateKeysAndObjectsUsingBlock: ^(id key, id obj, BOOL *stop) {
NSArray *valueArray = (NSArray *)obj;
for (NSDictionary * namesDict in valueArray) {
[names addObject:namesDict[#"name"]];
}
}];
}
Output:
NSLog(#"Names %#",names);
tango, ping, tango, ping.
Hope that helps!
Simply
for(NSDictionary *dict in firstObject){
NSLog(#"%#",[dict objectForKey:#"name"]);
}

iOS 7 NSJSONSerialization

I am trying to develop an app that parses json data. I have the following json :
{
myobject:[
{
id:184,
title: "test title"
}
]
}
I have the following code which im trying to get the title data from this json
NSData *jsonData = [NSData dataWithContentsOfURL:myURL];
NSError *error = nil;
NSDictionary *currentObject = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:&error];
if(error)
{
NSLog(#"%#",error);
}
NSDictionary *nar = [currentObject objectForKey:#"myobject"];
NSLog(#"%#",[nar valueForKey:#"title"]);
NSString *curTitle = [nar valueForKey:#"title"];
self.myTitle.text = curTitle;
When I log the title, I can see that the title is indeed coming back. However, when I try to set the myTitle.text I get the following error
Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[__NSArrayI length]: unrecognized selector sent to instance 0x15631850
In your json my object field is not a dictionary, but array of dictionaries, so [nar valueForKey:#"title"] will return array of valueForKey for each of elements in that array.
If you're sure about data format you can extract string value from it the following way:
 NSArray *nar = [currentObject objectForKey:#"myobject"];
NSString *curTitle = nar[0][#"title"];
But of course it is better to add some data validation/error handling in production code.
It is crash because Your dictionary contain NSArray, not dictionary.
NSArray *ar = [currentObject objectForKey:#"myobject"];
for(NSDictionary *dict in ar)
{
NSLog(#"%#", [dict objectForKey:#"title"];
)
}
NSString *curTitle = [[ar objectAtIndex:0] objectForKey:#"title"];
self.myTitle.text = curTitle;
You are trying to assign NSArray to self.myTitle.text.
NSData *jsonData = [NSData dataWithContentsOfURL:myURL];
NSError *error = nil;
NSDictionary *currentObject = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:&error];
if(error)
{
NSLog(#"%#",error);
}
NSArray *nar = [currentObject objectForKey:#"myobject"];
NSString *title = [[nar objectAtIndex:0] objectForKey:#"title"];
NSLog(#"%#",title);
self.myTitle.text = title;

Put value to a json response by using SBJson

I want to add value to a response. But the response is in this format
{
"participants": [
{
"lat_long": "0.0,0.0",
"name": "alma"
}
],
"lat_long": "0.0,0.0",
"_id": "52a80a5dccb8137326000027"
}
How can I add values to the keys name & lat_long. I am using Sbjson method.
Thanks in advance.
NSURL * url=[NSURL URLWithString:#"Give your URL Here"];
NSData * data=[NSData dataWithContentsOfURL:url];
NSError * error;
NSMutableDictionary * jsonDic=[NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableLeaves error:&error];
NSLog(#"%#",jsonDic);
NSMutableArray * jsonArray=jsonDic[#"participants"];
NSLog(#"%#",jsonArray);
NSString * str =[jsonArray valueForKey:#"lat_long"];
NSString * str1 =[jsonArray valueForKey:#"name"];
NSLog(#"%#",str);
NSLog(#"%#",str1);
Try this code.
I'm not sure, what you are asking about, but This helps you to get the keys of the Disctionary .
NSDictionary *json = [NSJSONSerialization .....//Parsed JSon
NSMutableDictionary *arrCopy = [json mutableCopy];
NSArray *keys= [json allKeys];
for (NSString *keysV in keys){
NSLog(#"Keys are %#", keysV);
if ([keysV isEqualToString:#"_id"]) {
[arrCopy setValue:#"121213211323" forKey:keysV];
}else if (){
}.......................
}
NSLog(#"After Value added: %#", arrCopy);

Create NSDictionary with keys and values when selected UICollectionViewCell

I have a UICollectionView with thumbnails. When user selects one or multiple images at same time, I have to create NSDictionary with keys and values. Key has to be a specific name. This is the final result I need to get.
(
image[0] = 75829457,
image[1] = 03480923,
image[2] = 58924589
)
Values here are obviously image ids. How can I do that? I need to send that NSDictionary via POST request, which is not a problem.
Any help would be appreciated.
Thank you.
create a method to get ImageDictionary
- (NSDictionary *) dictionaryWithImageArray:(NSArray *)imageArrayID
{
NSMutableDictionary *imageDict = [[NSMutableDictionary alloc] init];
for (int i=0; i<[imageArrayID count]; i++) {
[imageDict setObject:[imageArrayID objectAtIndex:i] forKey:[NSString stringWithFormat:#"image[%d]",i]];
}
return imageDict;
}
Convert that dict to json string
NSError *error;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:<Dict from above>
options:NSJSONWritingPrettyPrinted
error:&error];
NSString *jsonString= nil;
if (! jsonData) {
NSLog(#"Got an error: %#", error);
jsonString = #"";
} else {
jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}
Set Http Body for your request
[request setHTTPBody: [jsonString dataUsingEncoding:NSUTF8StringEncoding]];
In your controller, declare a member variable NSMutableString *mutableString. Initialize mutableString in your init method to be empty.
- (void)collectionView:(UICollectionView *)aCollectionView didSelectItemAtIndexPath:(NSIndexPath)indexPath {
NSString *key = [NSString stringWithFormat:#"image[%d]", [indexPath row]];
NSString *value = // get the picture id
NSString *parameter = [NSString stringWithFormat:#"%#=%#", key, value];
if ([mutableString length] != 0)
[mutableString appendString:#"&"];
[mutableString appendString:parameter];
}
Then use an IBAction to confirm the selections, construct your POST request and send it, and then empty the mutable string.

Resources