为啥 UIWebView 不在我的应用程序委托中的 applicationWillTerminate: 处加载 NSURLRequest?

Posted

技术标签:

【中文标题】为啥 UIWebView 不在我的应用程序委托中的 applicationWillTerminate: 处加载 NSURLRequest?【英文标题】:Why isn't UIWebView loading an NSURLRequest at applicationWillTerminate: in my app delegate?为什么 UIWebView 不在我的应用程序委托中的 applicationWillTerminate: 处加载 NSURLRequest? 【发布时间】:2013-12-20 21:20:17 【问题描述】:

我正在尝试在应用程序即将终止/进入后台时进行清理。

但是,当调用下面的代码时,

- (void)applicationWillTerminate:(UIApplication *)application

    NSURL* url = [NSURL URLWithString:@"http://www.mysite.com/mobile/home?sysmethod=proclogout&systype=mobile&pagetype=jquerymobile"];
    [self.webView loadRequest:[[NSURLRequest alloc] initWithURL:logoutURL]];

... 请求开始加载,但从未完成。我在 Apple 文档中读到,一旦 applicationWillTerminate: 被调用,应用程序有大约 5 秒的时间来完成他们正在做的事情。

我不相信这个过程会花费这么长时间,因为我在应用程序的其他地方加载了相同的请求,而且它总是在几毫秒内发生。

我已经尝试过同步和异步,没有运气无论哪种方式

感谢您的任何想法!

【问题讨论】:

applicationWillTerminate: 甚至不太可能被调用。你确认它被调用了吗?你的应用程序被杀死了。那时更新 Web 视图有什么意义?下次用户加载您的应用时,它将重新启动。 applicationWillTerminate 仅在您的应用程序进入后台(按设备的主页按钮的唯一选项)并且在应用程序的 info.plist 文件中设置“应用程序不在后台运行”键时才会调用“是的”。否则它永远不会被调用。你在用类似的东西吗? @AyanSengupta 在某些情况下,applicationWillTerminate 会在后台被调用——至少在 ios 7 中是这样。我不确定具体是什么时候,但在 iOS 7 发布之前我一直认为是同样的事情,而我的自己的应用开始在某些未知条件下调用该委托方法。 @rmaddy 它并不总是被调用。但是,当它存在时,我有一个未删除的打开会话(服务器端)。我的 loadRequest 是试图手动终止该会话。另请注意,我在 applicationDidEnterBackground 中执行了相同的步骤,结果相同。 @Hap 是的,这是终止应用程序的常用方法。但是applicationWillTerminate 只会在您的应用尚未转换到“暂停”状态时被调用。 【参考方案1】:

UIWebView 中的请求加载是异步的。这就解释了为什么请求开始加载但从未完成。如果您想确保调用或加载某个 URL,则必须以某种方式阻止 applicationWillTerminate: 方法退出。如果您不需要真正在 Web 视图中加载请求,则可以改用 [NSURLConnection sendSynchronousRequest:returningResponse:error:]

另外,一种 hacky 方法可能是这样的:

[_webview stringByEvaluatingjavascriptFromString:@"window.location.href=\"http://example.com/logout\""];

stringByEvaluatingJavaScriptFromString: 是一种阻塞的同步方法。但是,我没有尝试过它是否真的只有在请求完全加载后才会返回。它可能在设置位置后就已经返回。

【讨论】:

谢谢。这就是问题的根源。我正在使用 dispatch_async 加载我的所有请求(整个应用程序)。我现在看到的是多余的。但是,对于上述情况,我删除了 applicationWillTerminate 中的调度:以为我正在进行同步调用。 [NSURLConnection sendSynchronousRequest:returningResponse:error:] 确实有效,因为我真正想做的只是请求服务器终止我的会话(我不需要加载请求)。

以上是关于为啥 UIWebView 不在我的应用程序委托中的 applicationWillTerminate: 处加载 NSURLRequest?的主要内容,如果未能解决你的问题,请参考以下文章

@interface 中的 UIWebView 委托设置

UIWebView 中的 UIScrollView 的委托方法未调用水平滚动

UIwebView shouldStartLoadWithRequest 委托调用后需要点击手势方法

从 UIWebView 委托呈现 ViewController

为啥我的 UIwebView 内容在 iOS 中被截断?

UIWebView在Safari中打开链接