Objective-C获取网页时间 切换异步NSURLConnection请求后返回nil排查
问题根因
- 取值时机完全错误:
sendAsynchronousRequest属于异步执行接口,发起请求后不会阻塞当前线程继续执行,你在发起请求后立刻读取httpResponse的Date头字段时,网络请求还未返回,初始化的httpResponse本身就是空值,拿到的dateString自然为nil,后续格式化操作必然返回nil。 - 变量赋值逻辑错误:你将提取
dateString的逻辑写在了异步回调之外,回调中拿到的有效response对象完全没有被用来提取响应头,一开始定义的httpResponse变量从头到尾都没有被赋值。
排查方向
- 优先打印
dateString的原始值,确认是否本身就是空值,如果是空值直接排查请求链路的时机问题。 - 在异步回调内部打印完整的响应头字段,确认
Date字段是否正常返回,以及返回的格式是否和你设置的日期格式匹配。 - 检查日期格式化工具的locale配置,避免系统区域设置影响固定格式的日期解析。
解决方案
因为异步请求无法同步返回结果,你需要将原有的同步返回方法改造为异步回调形式,修正后的代码示例如下:
- (void)timeAndDateFromWebWithCompletion:(void(^)(NSDate * _Nullable date, BOOL hasConnection))completion { NSURL *url = [NSURL URLWithString:@"https://google.co.uk"]; NSURLRequest *urlRequest = [NSURLRequest requestWithURL:url]; NSOperationQueue *callbackQueue = [[NSOperationQueue alloc] init]; [NSURLConnection sendAsynchronousRequest:urlRequest queue:callbackQueue completionHandler:^(NSURLResponse *response, NSData *data, NSError *error) { BOOL hasDataConnection = NO; NSDate *resultDate = nil; if (!error && [response isKindOfClass:[NSHTTPURLResponse class]]) { hasDataConnection = YES; NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response; NSString *dateString = httpResponse.allHeaderFields[@"Date"]; if (dateString) { NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init]; dateFormatter.dateFormat = @"E, d MMM yyyy HH:mm:ss zzz"; // 使用en_US_POSIX避免用户自定义区域设置导致格式化失败,是固定格式日期解析的通用最佳实践 NSLocale *locale = [[NSLocale alloc] initWithLocaleIdentifier:@"en_US_POSIX"]; dateFormatter.locale = locale; resultDate = [dateFormatter dateFromString:dateString]; DebugLog(@" *** GOOGLE DATE: %@ ****", resultDate); } } // 如果后续需要操作UI,可统一回调到主线程 dispatch_async(dispatch_get_main_queue(), ^{ if (completion) { completion(resultDate, hasDataConnection); } }); }]; }
对应调用方式也需要调整为回调形式:
// 原同步调用方式:NSDate *date = [self timeAndDateFromWeb]; 不再可用,改为如下写法 [self timeAndDateFromWebWithCompletion:^(NSDate *date, BOOL hasConnection) { // 在此处处理拿到的时间和网络状态 if (date) { // 时间获取成功的逻辑 } }];
内容的提问来源于stack exchange,提问作者JSA986
相关产品推荐
相关产品推荐

