System.Net.WebException:发生SSL错误,无法建立与服务器的安全连接

时间:2019-02-02 09:33:59

标签: ios ssl xamarin.forms webexception

已经找到了相同的线程here,但这不能解决我的问题。

我已在info.plist中添加了NSAppTransportSecurityNSAllowsArbitraryLoads

截屏:

enter image description here

this文章中添加了以下代码。

<key>NSAppTransportSecurity</key>
    <dict>
        <key>NSAllowsArbitraryLoads</key>
        <true/>
        <key>NSExceptionDomains</key>
        <dict>
            <key>pm-admin.smartwcm.com</key>
            <dict>
                <key>NSIncludesSubdomains</key>
                <true/>
                <key>NSExceptionAllowInsecureHTTPSLoads</key>
                <true/>
                <key>NSExceptionRequiresForwardSecrecy</key>
                <true/>
                <key>NSExceptionMinimumTLSVersion</key>
                <string>TLSv1.1</string>
                <key>NSThirdPartyExceptionAllowInsecureHTTPSLoads</key>
                <false/>
                <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
                <true/>
                <key>NSThirdPartyExceptionMinimumTLSVersion</key>
                <string>TLSv1.1</string>
                <key>NSRequiresCertificateTransparency</key>
                <false/>
            </dict>
        </dict>
    </dict>

我正在使用HTTP REST API。运行项目时,出现以下异常:

  

System.Net.WebException:发生SSL错误,无法建立与服务器的安全连接。 ---> Foundation.NSErrorException:错误域= NSURLErrorDomain代码= -1200“发生SSL错误,无法建立与服务器的安全连接。” UserInfo = {NSLocalizedRecoverySuggestion =您是否仍要连接到服务器?

我错过了什么还是做错了什么?

2 个答案:

答案 0 :(得分:2)

原因:自iOS 9起,iOS仅允许您的应用程序与默认情况下实现最佳实践安全性的服务器通信。必须在Info.plist中设置值才能启用与不安全服务器的通信。似乎您只有AllowInsecureHTTPSLoads,却忘记添加AllowsInsecureHTTPLoads

解决方案:在您的info.plist中添加以下代码以信任您的域。

<key>NSAppTransportSecurity</key>
 <dict>
 <key>NSExceptionDomains</key>
 <dict>
  <key>pm-admin.smartwcm.com</key>
  <dict>       
   <key>NSExceptionRequiresForwardSecrecy</key>
   <false/>
   <key>NSExceptionAllowsInsecureHTTPLoads</key>
   <true/>
   <key>NSIncludesSubdomains</key>
   <true/>
   ...... 
  </dict>
 </dict>

这里是您可以参考的a similar issue

答案 1 :(得分:0)

因为必须使用证书。

class ViewController: UIViewController, URLSessionDelegate,URLSessionTaskDelegate {

var urlSession: Foundation.URLSession!

  override func viewDidLoad() {
        super.viewDidLoad()
        urlSession = URLSession(configuration: URLSessionConfiguration.default, delegate: self, delegateQueue: nil)
}

    func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {

        let serverTrust = challenge.protectionSpace.serverTrust
        let certificate = SecTrustGetCertificateAtIndex(serverTrust!, 0)
        let policies = NSMutableArray();
        policies.add(SecPolicyCreateSSL(true, (challenge.protectionSpace.host as CFString)))
        SecTrustSetPolicies(serverTrust!, policies);
        var result: SecTrustResultType = SecTrustResultType(rawValue: 0)!
        SecTrustEvaluate(serverTrust!, &result)
        let isServerTrusted:Bool = (result == SecTrustResultType.unspecified || result == SecTrustResultType.proceed)
        let remoteCertificateData:NSData = SecCertificateCopyData(certificate!)
        let pathToCert = Bundle.main.path(forResource: "certificateName", ofType: "crt")
        let localCertificate:NSData = NSData(contentsOfFile: pathToCert!)!
        let credential:URLCredential = URLCredential(trust: serverTrust!)
        completionHandler(.useCredential, credential)

    }


}