У меня есть следующая проблема. У меня есть модель, называемая пользователем. Когда пользователь теперь подключается к Facebook, мое приложение проверяет, существует ли пользователь в базе данных. Чтобы не замораживать пользовательский интерфейс (поскольку я прихожу с Android), я думал использовать NSURLConnection sendAsynchronousRequest
. Сначала работала следующая:Дождитесь завершения NSURLConnection sendAsynchronousRequest
В моей модели пользователя был метод, выполняющий всю задачу AsynchronousRequest
, а затем, когда законченный, установил переменную для загрузки. Тогда другие классы могли бы просто проверить с while (!user.loading)
, если Запрос был закончен или нет. Проблема, которая пришла сюда ко мне, заключалась в том, что теперь мне пришлось поместить этот метод в каждую модель. Поэтому вместо этого я создал новый класс HTTPPost
. Этот класс теперь имеет метод, который получает NSDictionary
и возвращает его. Это работает ПОЧТИ. Проблема, с которой я столкнулся сейчас, заключается в том, что я не мог определить, был ли процесс завершен или нет. Поэтому я начал создавать новый класс под названием Globals
и использовать глобальную переменную loading
. Но глобальная переменная ALWAYS NO. Итак, что было бы лучшим способом сделать это?
Вот мой код:
Это где я проверяю для пользователя и загрузить его. resultDictionary
является NSDictionary
, где все загружается в, но всегда nil
[user loadModelFrom:[NSString stringWithFormat:@"WHERE facebookId='%@'", graphUser.id]];
NSLog(@"%@", user.resultDictionary);
if (user.resultDictionary == nil) {
NSLog(@"NIL");
} else {
NSLog(@"NOT NIL");
}
Проблема сейчас в том, что, так как я послав AsynchronousRequest, то resultDictionary всегда равна нулю. То, что я делал раньше, и работало, было следующим.
В моей модели у меня был HTTP-запрос и переменная с именем loading
. Теперь я ставлю нагрузку на ложь, пока ответа не было сделано в NSDictionary
returnDict = [NSJSONSerialization JSONObjectWithData: [responseBody dataUsingEncoding:NSUTF8StringEncoding]
options: NSJSONReadingMutableContainers
error: &error];
Но тогда у меня была еще одна проблема. Я должен был сделать это во всех моих моделях снова ... Итак, я создал новый класс, который подклассы NSObject, который имеет асинхронныйRequest. Это целом запрос на
-(NSDictionary *)doHttpRequest:(NSDictionary *)postDict{
loading = NO;
__block NSDictionary *returnDict;
NSError *error;
NSString *jsonString;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:postDict
options:NSJSONWritingPrettyPrinted // Pass 0 if you don't care about the readability of the generated string
error:&error];
if (! jsonData) {
NSLog(@"Got an error: %@", error);
} else {
jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}
NSURL *aUrl = [NSURL URLWithString:@"http://xx.xx-xx.xx/xx.xx"];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:aUrl
cachePolicy:NSURLRequestUseProtocolCachePolicy
timeoutInterval:60.0];
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
NSString *authStr = [NSString stringWithFormat:@"%@:%@", @"xx", @"xx"];
NSData *authData = [authStr dataUsingEncoding:NSASCIIStringEncoding];
NSString *authValue = [NSString stringWithFormat:@"Basic %@", [authData base64EncodedString]];
[request setValue:authValue forHTTPHeaderField:@"Authorization"];
[request setValue:@"application/json" forHTTPHeaderField:@"Content-type"];
[request setHTTPMethod:@"POST"];
[request setHTTPBody:[jsonString dataUsingEncoding:NSUTF8StringEncoding]];
[NSURLConnection sendAsynchronousRequest:request queue:queue completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
{
NSString *responseBody = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
returnDict = [NSJSONSerialization JSONObjectWithData: [responseBody dataUsingEncoding:NSUTF8StringEncoding]
options: NSJSONReadingMutableContainers
error: &error];
}];
[queue waitUntilAllOperationsAreFinished];
loading = YES;
return returnDict;
}
Как вы можете видеть, что я есть сейчас переменную loading
. Это глобальная переменная. Но почему-то переменная всегда НЕТ.
Что было бы лучшим способом сделать это? Надеюсь, я понятен, я новичок в Objective-C, а английский - не мой родной язык.
UPDATE
Я изменил код, чтобы посмотреть, как пользователь представленная здесь, но до сих пор не работает!
HTTPPost.h
-(void)doHttpRequest:(NSDictionary *)postDict completion:(void(^)(NSDictionary *dict, NSError *error))completion {
__block NSDictionary *returnDict;
NSError *error;
NSString *jsonString;
NSString *authValue;
NSString *authStr;
NSData *jsonData;
NSData *authData;
NSURL *aUrl;
NSMutableURLRequest *request;
NSOperationQueue *queue;
jsonData = [NSJSONSerialization dataWithJSONObject:postDict
options:NSJSONWritingPrettyPrinted
error:&error];
if (! jsonData) {
NSLog(@"Got an error: %@", error);
} else {
jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}
aUrl = [NSURL URLWithString:@"http://xx.xx-xx.com/xx.php"];
request = [NSMutableURLRequest requestWithURL:aUrl
cachePolicy:NSURLRequestUseProtocolCachePolicy
timeoutInterval:60.0];
queue = [[NSOperationQueue alloc] init];
authStr = [NSString stringWithFormat:@"%@:%@", @"xx", @"xx"];
authData = [authStr dataUsingEncoding:NSASCIIStringEncoding];
authValue = [NSString stringWithFormat:@"Basic %@", [authData base64EncodedString]];
[request setValue:authValue forHTTPHeaderField:@"Authorization"];
[request setValue:@"application/json" forHTTPHeaderField:@"Content-type"];
[request setHTTPMethod:@"POST"];
[request setHTTPBody:[jsonString dataUsingEncoding:NSUTF8StringEncoding]];
[NSURLConnection sendAsynchronousRequest:request queue:queue completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
{
NSString *responseBody = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
returnDict = [NSJSONSerialization JSONObjectWithData: [responseBody dataUsingEncoding:NSUTF8StringEncoding]
options: NSJSONReadingMutableContainers
error: &error];
if (completion) {
completion(returnDict, error);
}
}];
}
//User.h
[_httpPost doHttpRequest:_dbDictionary completion:^(NSDictionary *dict, NSError *error) {
NSLog(@"completed") // NEVER GETS FIRED
}];
Привет, я сейчас дома, но это, кажется, хороший способ сделать. Я попробую завтра, а потом расскажу, как это получилось, но похоже, что это будет хорошо! – Musterknabe
Привет @Rob - Несчастливо это не работает. Я изменил свой первоначальный пост, так что теперь вы можете видеть, как это происходит на данный момент, и на самом деле это не работает. – Musterknabe
@Musterknabe Когда вы говорите «на самом деле не работает», что происходит? Я просто проверил ваш код на моем сервере (только заменив метод base-64), и он работал нормально. Я бы предложил установить точку останова и один шаг по вашему коду и выяснить, где он поступил неправильно. Если это не сбой, но вы не видите его полным, единственное, что я могу себе представить, это если ваша переменная _httpPost не была должным образом создана. Но код работает нормально. Если это произошло, обновите свой вопрос и сообщите нам, что именно произошло. См. Мой пересмотренный ответ для некоторых подробных наблюдений за вашим кодом. – Rob