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

使用WKWebView允许自签名证书但网页无法加载求助

解决WKWebView加载自签名HTTPS页面失败的问题

你的代码已经尝试处理证书信任逻辑,但有几个关键细节没处理到位,导致页面无法正常加载。我来帮你梳理问题并给出修正方案:

问题分析

你在didReceive challenge方法里直接强制信任所有证书,但没有先判断挑战是否属于服务器信任类型,而且强制解包serverTrust存在崩溃风险;另外WebView的布局方式也可能导致页面看似未加载(实际可能被布局问题隐藏)。

修正后的完整代码

override func viewDidLoad() {
    super.viewDidLoad()
    loadWebview(env_url:"https://myurl.com")
}

func loadWebview(env_url : String){
    let config = WKWebViewConfiguration()
    let controller = WKUserContentController()
    config.userContentController = controller
    
    // 安全解析URL,提前退出避免后续无效操作
    guard let url = URL(string: env_url) else {
        showAlertDebug(message: "Invalid URL")
        return
    }
    
    let urlRequest = URLRequest(url: url)
    webview = WKWebView(frame: view.bounds, configuration: config)
    
    // 先设置代理再加载请求,确保代理方法能被触发
    webview?.navigationDelegate = self
    webview?.uiDelegate = self
    webview?.allowsBackForwardNavigationGestures = true
    webview?.load(urlRequest)
    
    // 使用AutoLayout替代固定frame,适配所有屏幕尺寸
    view.addSubview(webview!)
    webview?.translatesAutoresizingMaskIntoConstraints = false
    NSLayoutConstraint.activate([
        webview!.topAnchor.constraint(equalTo: view.topAnchor),
        webview!.leadingAnchor.constraint(equalTo: view.leadingAnchor),
        webview!.trailingAnchor.constraint(equalTo: view.trailingAnchor),
        webview!.bottomAnchor.constraint(equalTo: view.bottomAnchor)
    ])
}

extension WebViewController : WKNavigationDelegate {
    func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
        decisionHandler(.allow)
    }
    
    func webView(_ webView: WKWebView, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
        // 只处理服务器信任类型的挑战,其他挑战交给系统默认处理
        guard challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodServerTrust,
              let serverTrust = challenge.protectionSpace.serverTrust else {
            completionHandler(.performDefaultHandling, nil)
            return
        }
        
        // 创建信任凭证并完成挑战
        let credential = URLCredential(trust: serverTrust)
        completionHandler(.useCredential, credential)
    }
}

extension WebViewController : WKUIDelegate { }

关键修改说明

  • 安全处理挑战类型:只针对服务器信任挑战做自定义逻辑,避免干扰客户端证书等其他认证流程
  • 可选值安全解包:用guard语句替代强制解包,防止因serverTrust为空导致崩溃
  • 优化WebView布局:使用AutoLayout适配屏幕,避免固定frame在不同设备上出现显示问题
  • 调整代码顺序:先设置代理再加载请求,确保代理方法能被正确触发

重要提醒

这种跳过证书验证的逻辑仅适合开发测试环境,正式上线必须使用CA颁发的合法证书,否则会带来严重的安全风险。如果需要在开发环境更严谨地验证自签名证书,还可以添加证书链校验、域名匹配等额外逻辑。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 09:47:29