Flutter webview 崩溃率上升怎么办?我的分析与解决方案

欢迎关注微信公众号:FSA全栈行动 👋

前言

我们 AppFlutter 版本从 3.27.4 升级到 3.29.3 并上线后,发现 Firebase Crashlytics 平台上多了一个仅 iOS 端才会的船新崩溃异常~

完整错误为:

ini 复制代码
Fatal Exception: NSInternalInconsistencyException
Completion handler passed to -[FWFNavigationDelegate webView:didReceiveAuthenticationChallenge:completionHandler:] was not called

除此之外,也有如下两个差不多的异常,只是没这个 AuthenticationChallenge 的多。

css 复制代码
Completion handler passed to -[webview_flutter_wkwebview.NavigationDelegateImpl webView:didReceiveAuthenticationChallenge:completionHandler:] was not called

Completion handler passed to -[webview_flutter_wkwebview.NavigationDelegateImpl webView:decidePolicyForNavigationResponse:decisionHandler:] was not called

崩溃的主要原因就是这些代理方法被调用后,其 completionHandler 必须也得被执行,否则就崩给你看。

相应的 issue : github.com/flutter/flu...

很奇怪,issue2022 年提的,提出人当时使用的 Flutter 版本是 2.10.4,直至今天这期间都有人断断续续提出在不同的 Flutter 版本上出现过,而我们是在升级至 3.29.3 才出现的~

经测试,目前最新版本的 Flutter 3.35.6webview_flutter_wkwebview 3.23.1 依旧可以复现。

复现

我们 App 涉及崩溃的设备有 98% 发生在后台状态

根据以往的经验,基本上可以断定是发生在上滑后杀掉 App 的那一刻,所以复现步骤也很简单:

1、Xcode 打全局断点并运行项目

2、进入内嵌页后,网页还在加载时立即上滑,再杀掉 App 即可

不过这也并不是百分之百复现的,既看时机,也看人,我也就十来次操作复现一次~

下图是我复现时的记录输出

可以看到崩溃时有多个 completionHandler 还没有被调用

修复

基于上述内容,基本上可以断定这个崩溃其实对用户来说是无感的,但是对我们 App 的崩溃率指标是敏感的,所以在官方修复之前,必须得有临时解决方案。

有两种方案,一是通过 Firebase 过滤掉此类崩溃,想法很好,但是 Firebase 并没有直接提供过滤功能,根据官方文档的说明,只能关闭自动收集崩溃上报功能,然后完全自定义上报异常,简直了,一个对用户无感的崩溃,不至于冒这么大的风险~

于是,Plan B 启动!

众所周知,iOS 是有黑魔法的,而刚好我之前就是搞 iOS 的。

核心思路:

  • 通过 Method Swizzling 将涉及崩溃的代理方法进行交换,进而监听方法调用和控制其 completionHandler 的调用
  • 在代理方法被调用时将 completionHandler 记录起来
  • completionHandler 被调用时删除记录
  • App 即将被杀掉时,对所有还未被调用的 completionHandler 执行调用

这个代码的实现过程就不带大家一步步分析了,有兴趣的小伙伴可以自行查看源码。

我已将修复代码进行了封装并发布了包

github.com/LinXunFeng/...

接下来看看如何使用

使用

添加依赖安装即可,无需其它额外配置,凑是这么方便~

yaml 复制代码
dependencies:
  webview_completion_fix: ^0.0.1

如果你想验证修复是否生效,可以在 ios/Runner/Info.plist 添加如下配置开启日志

xml 复制代码
<key>WCFEnableLogging</key>
<true/>

开启后如图会有 [WCF] 打头的日志输出

如倒数第 3 行所示,当杀掉 App 时,有 2completionHandler 还未被调用,并进行挽救调用防止崩溃。

最后

经过验证,我们新版本的 App 已经没有上报此类异常了~

好了,开源不易,如果你也觉得这个库好用,请不吝给个 Star 👍 ,并多多支持!

github.com/LinXunFeng/...

本篇到此结束,感谢大家的支持,我们下次再见! 👋

如果文章对您有所帮助, 请不吝点击关注一下我的微信公众号:FSA全栈行动, 这将是对我最大的激励. 公众号不仅有 iOS 技术,还有 AndroidFlutterPython 等文章, 可能有你想要了解的技能知识点哦~

相关推荐
游戏开发爱好者84 小时前
FTP 抓包分析实战,命令、被动主动模式要点、FTPS 与 SFTP 区别及真机取证流程
运维·服务器·网络·ios·小程序·uni-app·iphone
西西学代码6 小时前
Flutter---GridView+自定义控件
flutter
Nick56836 小时前
Xcode16 避坑
ios
ii_best6 小时前
IOS/ 安卓开发工具按键精灵Sys.GetAppList 函数使用指南:轻松获取设备已安装 APP 列表
android·开发语言·ios·编辑器
2501_915909067 小时前
iOS 26 文件管理实战,多工具组合下的 App 数据访问与系统日志调试方案
android·ios·小程序·https·uni-app·iphone·webview
hweiyu007 小时前
苹果iOS开发零基础特训(视频教程)
ios
hweiyu0011 小时前
Flutter零基础极速入门到进阶实战(视频教程)
flutter
hweiyu0012 小时前
Flutter高级进阶教程(视频教程)
flutter