iphoneobjective-cjsonjson-frameworksbjson

Unexpected end of input with SBJson in Objective-C


I have the following code that is trying to parse a JSON that I am returning from a website:

- (void)connectionDidFinishLoading:(NSURLConnection *)connection {

     [connection release];

     NSString *responseString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];

     NSLog(@"my ns string = %@", responseString);

     [responseData release];

     NSError *error; 
     NSDictionary *dictionary = [parser objectWithString:responseString   
                                               error:&error]; 
     while (error) { 
         NSLog(@"%@", error); 
         error = [[error userInfo] objectForKey:NSUnderlyingErrorKey]; 
     } 

     NSLog(@"%@", dictionary);


 }

I get these errors:

2011-08-01 20:16:47.273 myJSONParser[1040:b603] Connection didReceiveResponse: 
<NSHTTPURLResponse: 0x4e810f0> - application/json
2011-08-01 20:16:47.279 myJSONParser[1040:b603] Connection didReceiveData of length: 117
2011-08-01 20:16:47.359 myJSONParser[1040:b603] my ns string = 
2011-08-01 20:16:47.361 myJSONParser[1040:b603] Error Domain=org.brautaset.SBJsonParser.ErrorDomain Code=0 "Unexpected end of input" UserInfo=0x4eada30 {NSLocalizedDescription=Unexpected end of input}
2011-08-01 20:16:47.363 myJSONParser[1040:b603] (null)

I do have control over the JSON that I am trying to acquire and inside the PHP that generates the JSON I set the header like this:

header("Content-Type:application/json");
...
echo json_encode($arr);

"Unexpected end of input" leads me to believe that the JSON is somehow malformed, but JSONLint tells me its perfectly valid. What am I doing wrong? Thank you for taking the time to read through this, any advice would really be appreciated!

UPDATE:

I set the responseData like this:

NSMutableData *responseData;

- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
         NSLog(@"Connection didReceiveData of length: %u", data.length);

         [responseData appendData:data];

     }

And the parser like this (in .h):

SBJsonParser *parser;

And .m:

parser = [[SBJsonParser alloc] init];

Charles Findings:

HTTP/1.1 200 OK
Date: Tue, 02 Aug 2011 03:30:14 GMT
Server: Apache
X-Powered-By: PHP/5.2.15
Transfer-Encoding: chunked
Content-Type: application/json

[{"key1":"Name","key2":"First","key3":"2011-08-13"},{"key1":"Second","key2":"test2","key3":"2011-08-13"}]

Description of the NSData received:

Printing description of data: {length = 117, capacity = 256, bytes = 0x5b7b22686f6d65223a22426c61636b62 ... 30382d3133227d5d}


Solution

  • From the code, it looks like we only get "unexpected end of input" when the EOF token is found.

    SBJsonParser.m:

    case SBJsonStreamParserWaitingForData:
                self.error = @"Unexpected end of input";
                break;
    

    SBJsonStreamParserState.m:

    - (SBJsonStreamParserStatus)parserShouldReturn:(SBJsonStreamParser*)parser {
        return SBJsonStreamParserWaitingForData;
    }
    

    SBJsonStreamParser.m:

        switch (tok) {
            case sbjson_token_eof:
                return [state parserShouldReturn:self];
                break;
        ... }
    

    Your logs seem to indicate that something is wrong with the NSString. I would examine the response data to make sure it's correct--you can do this with a proxy like Fiddler or Charles, the xcode debugger, or just plain old NSLog().

    Edit:

    Ok I converted the data you got from the debugger to UTF-8 and this is what I got:

    [{"home":"Blackb ... 08-13"}]
    

    You only pasted a partial bit of the byte array, so there should be more where the ellipsis are. Does the 'home' or 'blackb' mean anything to you? It wan't anywhere in the response data that Charles intercepted. Do you do a setLength:0 on responseData in the didReceiveReponse delegate method?