You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter InAppWebView跨域Cookie在Android正常生效,但iOS端WebView仍重定向至登录页

Flutter InAppWebView跨域Cookie在Android正常生效,但iOS端WebView仍重定向至登录页

我之前也遇到过几乎一模一样的iOS WebView跨域Cookie问题,结合你的场景来看,核心原因是iOS WebKit(WKWebView)的隐私策略比Android WebView严格得多,尤其是跨顶级域(everest.7span.in和m.everest.7span.work分属.in和.work两个顶级域)的Cookie共享场景,很容易被系统拦截。下面是亲测有效的解决步骤:

1. 确保Cookie设置完成后再加载WebView

你当前在initState中异步调用_setCookies(),但WebView可能在Cookie还没设置完成时就发起了请求,导致登录态未生效。可以加个状态变量等待Cookie初始化完成:

class _HomeScreenState extends State<HomeScreen> {
  InAppWebViewController? _webViewController;
  final cookieManager = CookieManager.instance();
  final LogoutRepo repo = LogoutRepo();
  bool _isCookiesReady = false; // 新增状态变量

  @override
  void initState() {
    super.initState();
    _initCookiesThenLoadWebView();
  }

  // 先完成Cookie设置,再标记可加载WebView
  Future<void> _initCookiesThenLoadWebView() async {
    await _setCookies();
    setState(() => _isCookiesReady = true);
  }

  // ... 其他方法不变

  @override
  Widget build(BuildContext context) {
    return PopScope(
      canPop: false,
      onPopInvokedWithResult: (didPop, result) {
        if (!didPop) canBack();
      },
      child: Scaffold(
        body: Stack(
          children: [
            SafeArea(
              child: _isCookiesReady 
                  ? InAppWebView(/* 你的WebView配置 */)
                  : const Center(child: CircularProgressIndicator()),
            ),
          ],
        ),
      ),
    );
  }
}

2. 完善Cookie的属性配置

你已经设置了SameSite=None和Secure,但还需要补充path: '/'确保Cookie在API的所有路径下生效,同时确认domain配置准确:

Future<void> _setCookies() async {
  final token = await HiveService.getToken();
  final refreshToken = await HiveService.getRefreshToken();
  await cookieManager.deleteAllCookies();

  if (token != null) {
    await cookieManager.setCookie(
      url: WebUri("https://everest.7span.in"),
      name: "directus_session_token",
      value: token,
      domain: "everest.7span.in",
      path: "/", // 新增:确保全路径生效
      isSecure: true,
      isHttpOnly: true,
      sameSite: HTTPCookieSameSitePolicy.NONE,
    );
  }

  if (refreshToken != null) {
    await cookieManager.setCookie(
      url: WebUri("https://everest.7span.in"),
      name: "directus_refresh_token",
      value: refreshToken,
      domain: "everest.7span.in",
      path: "/", // 新增
      isSecure: true,
      isHttpOnly: true,
      sameSite: HTTPCookieSameSitePolicy.NONE,
    );
  }
}

3. 配置iOS Info.plist以绕过隐私限制

iOS 14+对跨域Cookie有严格的绑定要求,需要在ios/Runner/Info.plist中添加以下配置,声明App允许交互的域:

<!-- 允许WebView与指定域共享Cookie,避免被视为第三方Cookie拦截 -->
<key>WKAppBoundDomains</key>
<array>
  <string>everest.7span.in</string>
  <string>m.everest.7span.work</string>
</array>

<!-- 隐私权限描述,部分iOS版本需要这个才能允许跨域Cookie使用 -->
<key>NSUserTrackingUsageDescription</key>
<string>为了保持您的登录状态,需要使用Cookie进行身份验证</string>

4. 配置InAppWebView使用共享Cookie存储

在InAppWebViewSettings中指定使用共享的WebsiteDataStore,确保设置的Cookie能被WebView读取:

initialSettings: InAppWebViewSettings(
  javaScriptEnabled: true,
  useShouldOverrideUrlLoading: true,
  mediaPlaybackRequiresUserGesture: false,
  sharedCookiesEnabled: true,
  websiteDataStore: WebsiteDataStore.shared(), // 新增:使用共享存储
),

5. 额外排查点

  • 检查iOS系统设置:用户如果开启了「设置 -> Safari浏览器 -> 隐私与安全性 -> 阻止跨站跟踪」,会强制拦截第三方Cookie,你可以在App中提示用户关闭该设置。
  • 抓包验证:用Charles工具拦截iOS WebView的请求,查看请求everest.7span.in的API时,请求头是否包含Cookie字段:
    • 如果没有Cookie,说明是WebView未正确携带;
    • 如果有Cookie但后端返回无效,可能是后端的Cookie验证逻辑(比如SameSite检查、域名匹配)有问题。

内容来源于stack exchange

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.08 10:47:59