Become a MacRumors Supporter for $50/year with no ads, ability to filter front page stories, and private forums.

DennisBlah

macrumors 6502
Original poster
Dec 5, 2013
485
2
The Netherlands
Hi all,

I'm having an simple login in my app. When logged in it will go back to the main screen where it 'syncs' data.

At the start of this 'sync' it checks if there is an udid set and an session.
If so, we check this session, update it, and start the syncing.
i.e. user profile data.

Now, my NSURLConnection gives me an empty "session" value from my result once in the 3 or 4 times.

Here is how I retrieve it:
Code:
NSString *storedSession = [[applicationData firstObject] objectAtIndex: indexOfSession];
    
    NSURL *url=[NSURL URLWithString:@"http://mydomain.com/myApp/sessions.php?action=session"];
    NSString *post = [NSString stringWithFormat: @"user_udid=%@&user_appSession=%@", [[applicationData firstObject] objectAtIndex: indexOfUDID], [[applicationData firstObject] objectAtIndex: indexOfSession]];

    NSData *postData = [post dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES];
    
    NSString *postLength = [NSString stringWithFormat:@"%lu", [postData length]];
    
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
    [request setURL:url];
    [request setHTTPMethod:@"POST"];
    [request setValue:postLength forHTTPHeaderField:@"Content-Length"];
    [request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
    [request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
    [request setValue:@"Niesters-App" forHTTPHeaderField:@"User-Agent"];
    [request setHTTPBody:postData];
    //[NSURLRequest setAllowsAnyHTTPSCertificate:YES forHost:[url host]];
    
    NSError *error = [[NSError alloc] init];
    NSHTTPURLResponse *response = nil;
    NSData *urlData=[NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];

    if ([response statusCode] >=200 && [response statusCode] <300) {
        NSString *responseData = [[NSString alloc]initWithData:urlData encoding:NSUTF8StringEncoding];
        SBJsonParser *jsonParser = [SBJsonParser new];
        NSDictionary *jsonData = (NSDictionary *) [jsonParser objectWithString:responseData error:nil];
        NSInteger result = [(NSNumber *) [jsonData objectForKey:@"result"] integerValue];
        if(result == 0) {
            NSLog(@"No access.. incorrect session???");
            return NO;
        } else if(result == 1) {
            NSLog(@"Session check failed...");
            return NO;
        } else if(result == 2) {
            NSLog(@"Session check success!");
            NSString *session = [jsonData objectForKey: @"session"];

            NSLog(@"response: %@", responseData);
            //Cleanup data
            [appData truncatetable:@"userdata"];
            //Insert new data
//an insert query with the udid and session for later use.
//macrumors is kicking it out for security :-/
            [appData executeQuery:insertSession];
            return YES;
        } else {
            NSLog(@"Unknown... weird error...");
            return NO;
        }
    } else {
        serverConnection = NO;
        UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Connection Failed" message:@"Could not establish a connection with the server. The app data might not be up-to-date" delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil];
        [alert show];
        return NO;
    }
}

The result I get 1 out of 3/4 times, in my xcode console :
Code:
Session check success!
response: {"result":2,"session":"","userlevel":1}
It still goes pass, because the old session and the udid passed the php script. (result == 2)
But then still "session" is empty!?

Here comes the php script. (I simplified it, to always give session 'asd')

Code:
header('Content-type: application/json');
$result = '{"result":0}';


				if(valueSet($_POST['user_appSession'])) {

					$appSessionQ = $dbController->getQuery('user_id, user_level','dns_users','user_udid = "' . mysql_real_escape_string($_POST['user_udid']) . '" AND user_appSession = "' . mysql_real_escape_string($_POST['user_appSession']) . '"');
					if($appSessionQ !== 'none') {
						switch($action) {
							case 'session':
								$newSession = 'asd';//newAppSession();
								
								$updateQ = $dbController->updateQuery(array('user_appSession'),
																array(mysql_real_escape_string($newSession)),
																'users',
																'user_udid = "' . mysql_real_escape_string($_POST['user_udid']) . '" AND user_appSession = "' . mysql_real_escape_string($_POST['user_appSession']) . '"');
								if($updateQ !== 'error')
									$result = '{"result":2,"session":"' . $newSession . '","userlevel":' . $appSessionQ->user_level . '}';
								else
									$result = '{"result":1}';
							break;





echo $result;

(I kicked some things out. I also have an empty(action) : login)
When user_appSession is set
cases:
'udid' (also updates the device udid with the new one provided. and a new session)
'getAccount' (Will give me back my profile info)


All these cases are not kicking in, and is not to be discussed.

Is it possible that NSURLConnection sometimes does not get all information in the middle of the responseData ?

Even with session = 'asd' it comes back blank 1 out of 3/4 times.

However when I do this from my browser, it keeps working. I can keep bombing the page, but it keeps working.
 
Last edited:
I don't see any kind of error handling for the sendSynchronousRequest. The return value is not checked for NULL and the error variable isn't examined. Is it possible the Request isn't succeeding? Or maybe you just took the error handling out when showing your sample code to simplify.
 
I have no idea.

Is it possible that you're getting back a cached response of some kind?

I don't see how I could get an cached result tho :s
Even if.. Why is it empty? I NEVER have an empty session returned.
Either I receive 'asd' or result = 0 or 1 without any more values

I don't see any kind of error handling for the sendSynchronousRequest. The return value is not checked for NULL and the error variable isn't examined. Is it possible the Request isn't succeeding? Or maybe you just took the error handling out when showing your sample code to simplify.

Ehm no I do not actually :-$
But.. I don't think it'll give me an error since the responsecode is fine and will not reach an else as it's within this range.
Code:
 if ([response statusCode] >=200 && [response statusCode] <300) {

So it will never reach:
Code:
} else {
    NSLog(@"Some connection issue");
    if (error) NSLog(@"Error: %@", error);
}
The return value, is not NULL, because the returned value is:
{"result":2,"session":"","userlevel":1}

That's the most strangest thing... Even tho, the PHP ALWAYS returns 'asd' in "session"

If the return was NULL, xcode would not know that I'm in the if(result == 2) and would not give me an 'success' and the returned value.

As you see in the PHP, my default result is 0

So or.. I get an 0 back, when the 'request' is incorrect, 1 when it failed for example credentials failed or some sql injection, or a 2 which succeed, and will also give an userlevel and a session for my app.





----

To be honest, I don't even know quite well why I'm doing it this way, except for the fact I need to POST vars to the script.

like this
Code:
NSString *authURL = [NSString stringWithFormat: @"%@/checkAuth.php?udid=%@", theHost, UDID];
        NSData *authData = [NSData dataWithContentsOfURL: [NSURL URLWithString: authURL]];
        NSString *authResult = [[NSString alloc] initWithData: authData encoding: NSUTF8StringEncoding];

Is something from another application I made, which authenticates the device to an simple file on a server based on UDID.

I'm still kinda new into xCode, I got a lot to learn, even tho it's still obj-c

Maybe there is a simpler way to send a POST call to an page ?
I'm gonna give it a try with the RestKit library however it will increase the size of my app since the library alone is already 1.5mb

Please advice


-----


My appologies for everyone who is looking into this topic.
This is an PHP fault.

On the moment the unit receives a new UDID, I do trigger a different case in php
which will update the new udid to the user, and ofcourse a new session.

However, the $newSession is never being set with a session in this php case.

Thanks all!
 
Last edited:
Register on MacRumors! This sidebar will go away, and you'll see fewer ads.