有趣的编程难题......
我无法将错误初始化为nil,因此下面的代码会崩溃。
NSString *query = [NSString stringWithFormat:@"http://mysite.com/getlatest.php?a=%@", aSuiteName];
NSURL *url = [NSURL URLWithString:query];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url cachePolicy:NSURLCacheStorageNotAllowed timeoutInterval:10];
[request setHTTPMethod:@"GET"];
NSURLResponse *response = nil;
NSError *error;
NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
if ( !data || error != nil ) {
NSLog(@"Error downlading %@", error); //CRASH
return NO;
}
我的问题是,如何让我的服务器返回一个错误,例如sendSynchronousRequest:returningResponse:error:实际上收到错误,但仍然继续下载数据?某种非致命错误会导致错误被初始化为NSError对象吗?
这与类似的难题有关,我之前想要在没有完全失败的情况下返回状态信息。所以,虽然模糊不清,但我很想知道是否有这种技术。
虽然这是一个Cocoa问题,但我认为答案将在php中。像
这样的东西<?php
header( set 503 error here );
return data;
?>
答案 0 :(得分:0)
我通过将数据包装到NSError对象中来处理这个问题。在纯文本响应的情况下,我还将响应用作localizedDescription。我使用单独的方法来评估结果是否成功。如果URL请求本身生成错误,我也认为这是一个失败,并传递URL请求提供的NSError。
这是从我的ServerRequest类中删除的:
+ (NSError *) errorForStatusCode:(NSInteger) statusCode
contentType:(NSString *) contentType
textEncodingName:(NSString *) textEncodingName
data:(NSData *) data {
NSMutableDictionary *userInfo = [NSMutableDictionary dictionary];
if ([contentType isEqualToString:@"text/plain"]) {
[userInfo setValue:[[NSString alloc] initWithData:data encoding:[self stringEncodingForTextEncodingName:textEncodingName]]
forKey:NSLocalizedDescriptionKey];
} else if ( ... ) {
// handle other relevant types
}
return [NSError errorWithDomain:[[self class] description]
code:statusCode
userInfo:userInfo];
}
- (BOOL) statusCodeIndicatesSuccess:(NSInteger) statusCodeValue {
return 201 == statusCodeValue; // Modify this based on your API
}
- (BOOL) runSynchronouslyReturningResult:(NSData **) resultPtr error:(NSError **) errorPtr {
NSHTTPURLResponse *response = nil;
NSError *error = nil;
NSData *result = [NSURLConnection sendSynchronousRequest:[self request] returningResponse:&response error:&error];
if (error) {
if (errorPtr) *errorPtr = error;
return NO;
}
self.statusCode = [response statusCode];
self.MIMEType = [response MIMEType];
self.textEncodingName = [response textEncodingName];
if ([self statusCodeIndicatesSuccess:self.statusCode]) {
if (resultPtr) *resultPtr = result;
return YES;
} else {
if (errorPtr) *errorPtr = [ServerRequest errorForStatusCode:self.statusCode
contentType:self.MIMEType
textEncodingName:self.textEncodingName
data:result];
if (resultPtr) *resultPtr = result;
return NO;
}
}