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

Flutter WebView集成Stripe Checkout安卓报错:需设置allow-same-origin

问题原因分析
  1. 安卓WebView对data:URL的沙箱限制:data:协议加载的HTML默认处于无同源的沙箱环境,且Cookie被强制禁用,而Stripe.js运行需要同源权限(allow-same-origin)和Cookie支持,直接触发了"Stripe.js requires 'allow-same-origin' if sandboxed"及Cookie读取失败的错误。
  2. Content-Security-Policy设置无效:在loadRequest的headers中设置CSP对data:URL无效,因为data协议的资源不遵循常规HTTP头部规则。
  3. 安卓WebView未启用Payment特性:"Unrecognized feature: 'payment'"报错说明安卓WebView默认未开启Payment API支持,影响Stripe脚本初始化。
解决方案

方案一:改用本地Asset文件加载HTML(推荐)

将HTML内容保存为本地Asset文件,通过asset协议加载,让WebView赋予其正常的同源环境,绕过data:URL的沙箱限制。

步骤1:配置Asset文件

  1. 在项目根目录创建assets文件夹,新建stripe_checkout.html文件,内容如下:
<!DOCTYPE html>
<html>
  <script src="https://js.stripe.com/v3/"></script>
  <style>
    body, html {
      width: 100%;
      height: 100%;
      margin: 0;
      padding: 0;
    }
    #loader {
      width: 100%;
      height: 100%;
      display: flex;
      justify-content: center;
      align-items: center; 
    }
  </style>
  <head><title>Stripe checkout</title></head>
  <body>
    <div id="loader">
      <span>Please wait...</span>
    </div>
  </body>
</html>
  1. 在pubspec.yaml中添加Asset引用:
flutter:
  assets:
    - assets/stripe_checkout.html

步骤2:修改Flutter代码

更新CheckoutPage的initialUrl和WebViewController配置:

class _CheckoutPageState extends State<CheckoutPage> {
  late WebViewController _controller;

  @override
  void initState() {
    super.initState();
    _controller = WebViewController()
      ..clearCache()
      ..setJavaScriptMode(JavaScriptMode.unrestricted)
      // 安卓端启用必要设置
      ..androidSettings = const AndroidWebSettings(
        domStorageEnabled: true,
        javaScriptCanOpenWindowsAutomatically: true,
        allowContentAccess: true,
        allowFileAccess: true,
        databaseEnabled: true,
      )
      ..setNavigationDelegate(NavigationDelegate(
        onNavigationRequest: (NavigationRequest request) {
          if (request.url.startsWith(checkoutSuccessUrl)) {
            context.pop('success');
          } else if (request.url.startsWith(checkoutFailureUrl)) {
            context.pop('cancel');
          }
          return NavigationDecision.navigate;
        },
        onPageFinished: (String url) {
          if (url.startsWith('asset:///assets/stripe_checkout.html')) {
            _redirectToStripe();
          }
        },
        onWebResourceError: (error) {
          print(error);
        },
      ))
      ..loadRequest(Uri.parse(initialUrl));
  }

  // 修改为Asset路径
  String get initialUrl => 'asset:///assets/stripe_checkout.html';

  void _redirectToStripe() {
    final redirectToCheckoutJs = '''
      var stripe = Stripe('$stripePublicKey');
      stripe.redirectToCheckout({
        sessionId: '${widget.sessionId}'
      }).then(function (result) {
        if (result.error) {
          console.error(result.error.message);
        }
      });
    ''';
    _controller.runJavaScript(redirectToCheckoutJs);
  }

  // 其余代码保持不变
}

方案二:调整安卓WebView沙箱与Cookie设置(备选)

如果必须使用data:URL,需通过安卓原生配置解除沙箱限制并启用Cookie:

步骤1:启用Cookie支持

在initState中添加Cookie初始化代码:

import 'package:webview_flutter/webview_flutter.dart';
import 'dart:io';

@override
void initState() {
  super.initState();
  // 安卓端启用Cookie
  if (Platform.isAndroid) {
    final cookieManager = CookieManager();
    cookieManager.setCookie(
      url: 'https://js.stripe.com',
      name: 'stripe_session',
      value: '',
      domain: 'js.stripe.com',
      path: '/',
      expires: DateTime.now().add(const Duration(days: 365)),
      isSecure: true,
    );
  }
  // 其余WebViewController初始化代码...
}

步骤2:修改WebView沙箱设置

通过安卓原生WebSettings解除沙箱限制:

_controller.androidSettings = AndroidWebSettings(
  allowContentAccess: true,
  allowFileAccess: true,
  allowUniversalAccessFromFileURLs: true,
  domStorageEnabled: true,
  javaScriptCanOpenWindowsAutomatically: true,
  setSupportMultipleWindows: true,
);
关键注意事项
  • iOS对data:URL的沙箱限制更宽松,因此无此问题,但安卓需严格遵循同源策略。
  • 务必确保stripePublicKey和sessionId正确无误,避免因参数错误导致跳转失败。
  • 测试时启用WebView调试(AndroidWebViewController.enableDebugging(true)),方便查看控制台日志定位问题。

内容的提问来源于stack exchange,提问作者Tanjim ahmed

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.29 04:33:11