JSON Parsing Error (blank response) - objective-c

Here's my code, when I run it, I get: "2014-10-26 19:02:09.153 App[27372:1281902] Price: (
)".
I was wondering why, no errors are being passed through and it honestly confuses me.
(I'm getting a blank response for "omc_usd_price")
#try
{
NSURL *url = [NSURL URLWithString:#"https://omnicha.in/api?method=getinfo"];
NSData *data=[NSData dataWithContentsOfURL:url];
NSError *error;
NSMutableDictionary *JSONStuff= [NSJSONSerialization JSONObjectWithData:data options: NSJSONReadingMutableContainers error: &error];
NSLog(#"%#",JSONStuff);
NSMutableArray * OMCArray = [[NSMutableArray alloc]init];
NSArray * responseArr = JSONStuff[#"omc_usd_price"];
for(NSDictionary * dict in responseArr)
{
[OMCArray addObject:[dict valueForKey:#"omc_usd_price"]];
}
NSLog(#"Price: %# test", OMCArray); // Here you get the Referance data
}
#catch (NSException *exception) {
NSLog(#"%#", exception);
}
#finally {
}
EDIT:
Tried this, I don't think I did this right either!
NSMutableArray * OMCArray = [[NSMutableArray alloc]init];
NSMutableArray * OMCArray2 = [[NSMutableArray alloc]init];
NSArray * responseArr = JSONStuff[#"response"];
NSArray * responseArr2 = JSONStuff[#"omc_usd_price"];
for(NSDictionary * dict in responseArr)
{
[OMCArray addObject:[dict valueForKey:#"response"]];
for(NSDictionary * dict2 in responseArr2)
{
[OMCArray addObject:[dict2 valueForKey:#"omc_usd_price"]];
}
}
NSLog(#"Price: %# test", OMCArray2); // Here you get the Referance data

Here is the JSONStuff dictionary:
{
"error":false,
"response":{
"block_count":96136,
"difficulty":12.18364177,
"netmhps":234.652099,
"seconds_since_block":694,
"avg_block_time":196.533,
"total_mined_omc":6426691.6,
"omc_btc_price":7.0e-6,
"omc_usd_price":0.0025,
"market_cap":15833.5909
}
}
As you can see, there is no entry in the dictionary named "omc_usd_price". There is a entry by that name in the dictionary name "response", but you didn't ask for that.

If you want to get omc_usd_price, as mentioned on your code, then you need to parse 2 dictionaries.
You must first parse the dictionary with the key response, and this will give you a new dictionary.
Then in this new dictionary you must parse/look for the key omc_usd_price.
Also, you're not getting an array back, but a double or float or even a string.

Related

how to parse this JSON in OBJ c

I receive this JSON string from a web process
{
"result":"ok",
"description":"",
"err_data":"",
"data":[
{
"id":"14D19A9B-3D65-4FE2-9ACE-4C2D708DAAD8"
},
{
"id":"8BFD10B8-F5FD-4CEE-A307-FE4382A0A7FD"
}
]
}
and when I use the following to get the data:
NSError *jsonError = nil;
NSData *objectData = [ret dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *json= [NSJSONSerialization JSONObjectWithData: objectData options:kNilOptions error: &jsonError];
NSLog(#"data: %#",[json objectForKey:#"data"]);
it gets logged as:
(
{
id = "14D19A9B-3D65-4FE2-9ACE-4C2D708DAAD8";
},
{
id = "8BFD10B8-F5FD-4CEE-A307-FE4382A0A7FD";
}
)
How can I parse the data as an NSDictionary with value and keys?
The web returns an object that has a property which is an array of objects, so...
NSDictionary *json= // your code
NSArray *array = json[#"data"];
for (NSDictionary *element in array) {
NSLog(#"%#", element);
// or, digging a little deeper
NSString *idString = element[#"id"];
NSLog(#"id=%#", idString);
}

how to convert an array into string? [duplicate]

In my iPhone aplication I have a list of custom objects. I need to create a json string from them. How I can implement this with SBJSON or iPhone sdk?
NSArray* eventsForUpload = [app.dataService.coreDataHelper fetchInstancesOf:#"Event" where:#"isForUpload" is:[NSNumber numberWithBool:YES]];
SBJsonWriter *writer = [[SBJsonWriter alloc] init];
NSString *actionLinksStr = [writer stringWithObject:eventsForUpload];
and i get empty result.
This process is really simple now, you don't have to use external libraries,
Do it this way, (iOS 5 & above)
NSArray *myArray;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:myArray options:NSJSONWritingPrettyPrinted error:&error];
NSString *jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
I love my categories so I do this kind of thing as follows
#implementation NSArray (Extensions)
- (NSString*)json
{
NSString* json = nil;
NSError* error = nil;
NSData *data = [NSJSONSerialization dataWithJSONObject:self options:NSJSONWritingPrettyPrinted error:&error];
json = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
return (error ? nil : json);
}
#end
Although the highest voted answer is valid for an array of dictionaries or other serializable objects, it's not valid for custom objects.
Here is the thing, you'll need to loop through your array and get the dictionary representation of each object and add it to a new array to be serialized.
NSString *offersJSONString = #"";
if(offers)
{
NSMutableArray *offersJSONArray = [NSMutableArray array];
for (Offer *offer in offers)
{
[offersJSONArray addObject:[offer dictionaryRepresentation]];
}
NSData *offersJSONData = [NSJSONSerialization dataWithJSONObject:offersJSONArray options:NSJSONWritingPrettyPrinted error:&error];
offersJSONString = [[NSString alloc] initWithData:offersJSONData encoding:NSUTF8StringEncoding] ;
}
As for the dictionaryRepresentation method in the Offer class:
- (NSDictionary *)dictionaryRepresentation
{
NSMutableDictionary *mutableDict = [NSMutableDictionary dictionary];
[mutableDict setValue:self.title forKey:#"title"];
return [NSDictionary dictionaryWithDictionary:mutableDict];
}
Try like this Swift 2.3
let consArray = [1,2,3,4,5,6]
var jsonString : String = ""
do
{
if let postData : NSData = try NSJSONSerialization.dataWithJSONObject(consArray, options: NSJSONWritingOptions.PrettyPrinted)
{
jsonString = NSString(data: postData, encoding: NSUTF8StringEncoding)! as String
}
}
catch
{
print(error)
}
Try like this,
- (NSString *)JSONRepresentation {
SBJsonWriter *jsonWriter = [SBJsonWriter new];
NSString *json = [jsonWriter stringWithObject:self];
if (!json)
[jsonWriter release];
return json;
}
then call this like,
NSString *jsonString = [array JSONRepresentation];
Hope it will helps you...
I'm a bit late to this party, but you can serialise an array of custom objects by implementing the -proxyForJson method in your custom objects. (Or in a category on your custom objects.)
For an example.

Filtering Parsed JSON in Objective-C

I'm trying to take out the "lasttradeprice" in https://www.allcrypt.com/api.php?method=singlemarketdata&marketid=672 but I can't seem to figure out how to grab the "lasttradeprice" piece.
How would I 'filter' the "price" out? None of the other information is relevant.
Current Code:
NSURL * url=[NSURL URLWithString:#"https://www.allcrypt.com/api.php?method=singlemarketdata&marketid=672"]; // pass your URL Here.
NSData * data=[NSData dataWithContentsOfURL:url];
NSError * error;
NSMutableDictionary * json = [NSJSONSerialization JSONObjectWithData:data options: NSJSONReadingMutableContainers error: &error];
NSLog(#"%#",json);
NSMutableArray * referanceArray=[[NSMutableArray alloc]init];
NSMutableArray * periodArray=[[NSMutableArray alloc]init];
NSArray * responseArr = json[#"lasttradeprice"];
for(NSDictionary * dict in responseArr)
{
[referanceArray addObject:[dict valueForKey:#"lasttradeprice"]];
[periodArray addObject:[dict valueForKey:#"lasttradeprice"]];
}
NSLog(#"%#",referanceArray);
NSLog(#"%#",periodArray);
NOTE: Keep in mind I've never worked with JSON before so please keep your answers dumbed down a tad.
Key value coding provides an easy way to dig through that data. Use the key path for the values you want. For example, it looks like you could get the array of recent trades using the path "return.markets.OMC.recenttrades" like this (assuming your code to get the json dictionary):
NSArray *trades = [json valueForKeyPath:#"return.markets.OMC.recenttrades"];
That's a lot more concise than having to dig down one level at a time.
The value returned for a given key by an array is the array of values returned by the array's members for that key. In other words, you can do this:
NSArray *recentprices = [trades valueForKey:#"price"];
And since that's just the next step in the key path, you can combine the two operations above into one:
NSArray *recentprices = [json valueforKeyPath:#"return.markets.OMC.recenttrades.price"];
The only down side here is that there's no real error checking -- either the data matches your expectations and you get back your array of prices, or it doesn't match at some level and you get nil. That's fine in some cases, not so much in others.
Putting that together with the relevant part of your code, we get:
NSURL *url = [NSURL URLWithString:#"https://www.allcrypt.com/api.php?method=singlemarketdata&marketid=672"];
NSData *data = [NSData dataWithContentsOfURL:url];
NSError *error = nil;
NSMutableDictionary *json = [NSJSONSerialization JSONObjectWithData:data options: NSJSONReadingMutableContainers error:&error];
NSArray *recentprices = [json valueforKeyPath:#"return.markets.OMC.recenttrades.price"];
Update: I just noticed that you want the "lasttradeprice", not the array of prices. Given that, the key path to use is simply #"return.markets.OMC.lasttradeprice", and the value you'll get back will be a string. So replace the last line above with:
NSString *lastTradePrice = [json valueforKeyPath:#"return.markets.OMC.lasttradeprice"];
The value you want is buried a few dictionaries deep. One general idea might be to dig recursively, something like this:
- (BOOL)isCollection:(id)object {
return [object isKindOfClass:[NSArray self]] || [object isKindOfClass:[NSDictionary self]];
}
- (void)valuesForDeepKey:(id)key in:(id)collection results:(NSMutableArray *)results {
if ([collection isKindOfClass:[NSDictionary self]]) {
NSDictionary *dictionary = (NSDictionary *)collection;
if (dictionary[key]) [results addObject:dictionary[key]];
for (id deeperKey in [dictionary allKeys]) {
if ([self isCollection:dictionary[deeperKey]]) {
[self valuesForDeepKey:key in:dictionary[deeperKey] results:results];
}
}
} else if ([collection isKindOfClass:[NSArray self]]) {
NSArray *array = (NSArray *)collection;
for (id object in array) {
if ([self isCollection:object]) {
[self valuesForDeepKey:key in:object results:results];
}
}
}
}
Then call it like this:
NSMutableArray *a = [NSMutableArray array];
[self valuesForDeepKey:#"lasttradeprice" in:json results:a];
NSLog(#"%#", a);

Parsing JSON: Checking for object existence and reading values

My application returns a NSMutableData *receivedData.
I've opted for using NSJSONSerialization to parse this under the assumption that it would be easiest. I'm having extreme trouble trying to get my head around how to do it. I'm very new to Objective-C, from a Java background.
In Java I used gson to parse the JSON in to an array which I could use easily. I'm really struggling with this here.
My current code for parsing the JSON is:
NSError *e = nil;
NSArray *jsonArray = [NSJSONSerialization JSONObjectWithData: receivedData options: NSJSONReadingMutableContainers error: &e];
if (!jsonArray) {
NSLog(#"Error parsing JSON: %#", e);
} else {
for(NSDictionary *item in jsonArray) {
NSLog(#"Item: %#", item);
}
}
As provided by somebody on the internet. This works and prints two items to NSLog. result and header. Here is how the JSON looks:
{
"header":{
"session":"sessionid",
"serviceVersion":"1",
"prefetchEnabled":true
},
"result":"50ce82401e826"
}
However if there is an error the JSON can also look like this:
{
"header":{
"session":"sessionid",
"serviceVersion":"1",
"prefetchEnabled":true
},
"fault":{
"code":0,
"message":"someErrorCode"
}
}
How I want the code to work:
Check if there is a "fault" object
If there is, print fault.code and fault.message to NSLog
If there isn't, I know that my JSON contains result instead of fault
Print the value of result to NSLog
But I can't for the life of me figure out how to approach it. Can someone please give me some pointers?
your object appears to be a dictionary.
Try this out.
NSError *e = nil;
id jsonObj = [NSJSONSerialization JSONObjectWithData: receivedData options: NSJSONReadingMutableContainers error: &e];
NSArray *jsonArray = nil;
NSDictionary *jsonDict = nil;
if ([jsonObj isKindOfClass:[NSArray class]]){
jsonArray = (NSArray*)jsonObj;
}
else if ([jsonObj isKindOfClass:[NSDictionary class]]){
jsonDict = (NSDictionary*)jsonObj;
}
if (jsonArray != nil) {
// you have an array;
for(NSDictionary *item in jsonArray) {
NSLog(#"Item: %#", item);
}
}
else if (jsonDict != nil){
for (NSString *key in jsonDict.allKeys){
NSLog(#"Key: %# forItem: %#",key,[jsonDict valueForKey:key]);
}
}
else {
NSLog(#"Error: %#",e);
}

Unrecognized selector error when indexing into a dictionary of arrays

I have a dictionary of arrays that is causing __NSCFDictionary objectAtIndex: errors.
Can someone tell me why? The dictionary clearly has at least 1 array at the time of the error.
NSError *error;
responseString = [[NSString alloc] initWithData:self.responseData2 encoding:NSUTF8StringEncoding];
/* response string contains this:
{"words":
{
"word": {"rowsreturned":0,"id":"-1","date":"","word":"","term":"","definition":"","updated_on":""}
},
"status":"",
"rowsreturned":""
}
*/
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:self.responseData2 options:kNilOptions error:&error];
NSArray *todaysWord = [[json objectForKey:#"words"] objectForKey:#"word"];
//error here -[__NSCFDictionary objectAtIndex:]: unrecognized selector sent to instance
NSDictionary *word = [todaysWord objectAtIndex:0];
In your case [[json objectForKey:#"words"] objectForKey:#"word"]; is returning a dictionary and not an array. Try doing the following,
id wordParam = [[json objectForKey:#"words"] objectForKey:#"word"];
if ([wordParam isKindOfClass:[NSArray class]]) {
NSDictionary *word = [(NSArray *)wordParam objectAtIndex:0];
} else if ([wordParam isKindOfClass:[NSDictionary class]]) {
NSDictionary *word = (NSDictionary *)wordParam;
} else {
NSLog(#"error. %# is not an array or dictionary", wordParam);
}
Your response string also shows that value for word is,
{"rowsreturned":0,"id":"-1","date":"","word":"","term":"","definition":"","updated_on":""}
which is a dictionary with key value pairs as rowsreturned:0, id:-1 etc..