• iOS9中关于 NSURLSession/NSURLConnection HTTP load failed 的解决办法


    最近为了新的存管app上线,忙了近一个月,重新过了一段996的日子,今天终于可以喘口气,继续更新博客了。本文记录一下在iOS 9中发送https请求遇到的问题及解决办法,希望通过本文,可以对ATS 的配置有一个更深入的了解。

    问题描述

    在开发app时,遇到了在iOS 9中发送https请求报错的问题:

    NSURLSession/NSURLConnection HTTP load failed (kCFStreamErrorDomainSSL, -9801)
    

    我们知道,在iOS 9以后,所有的网络请求默认使用https,如果你发送http请求,则会报如下错误,但是我们可以通过在info.plist中设置NSAppTransportSecurity - NSAllowsArbitraryLoads的值为YES来允许http请求:

    App Transport Security has blocked a cleartext HTTP (http://) resource load since it is insecure. Temporary exceptions can be configured via your app's Info.plist file.
    

    info.plist

    允许http请求

    这样解决了http的请求问题,但是我发送是https请求,还是出现HTTP laod failed的问题,尽管使用上述方法也可以解决,但这不是根本的解决办法。

    解决办法

    经过分析,怀疑是TLS的问题,因为iOS 9默认需要TLS1.2版本来加密数据,如果服务端不支持TLS1.2,则URLSession:task:didCompleteWithError:会返回nilerror,但是后端开发同事说服务器支持TLS1.0TLS1.1TLS1.2,这好像又不是TLS的问题。于是不放心,用nscurl测试了一下测试服务器,果然不支持TLS1.2,问题找到。

    # 加 --verbose 是为了显示详细的调试信息
    /usr/bin/nscurl --ats-diagnostics --verbose https://testresource.chaoaicai.com
    

    通过输出看出,服务器只支持TLS1.0,于是让后台开发的同事测试并修改后,再次测试,发现服务器支持TLS1.2了,并且https的网络请求也正常了。

    支持TLS1.2

    ATS异常配置

    其实,针对服务器不支持TLS1.2,而客户端发送https请求还有其它的解决方法,就是配置ATS,设置最低的TLS版本即可,如下info.plist所示:

    <key>NSAppTransportSecurity</key>
      <dict>
      <key>NSExceptionDomains</key>
      <dict>
        <!--你的https域名-->
        <key>testresource.chaoaicai.com</key>
        <dict>
          <!--允许子域-->
          <key>NSIncludesSubdomains</key>
          <true/>
          <!--TLS允许的最低版本号-->
          <key>NSExceptionMinimumTLSVersion</key>
          <string>TLSv1.0</string>
        </dict>
      </dict>
    </dict>
    

    其中,NSExceptionDomains的具体设置项介绍如下,可以更详细的了解ATS的异常配置

    • NSIncludesSubdomains:是否应用到子域名,默认是NO
    • NSExceptionAllowsInsecureHTTPLoads:是否允许http请求,YES(允许),默认是NO
    • NSExceptionMinimumTLSVersion:最低的TLS版本
    • NSExceptionRequiresForwardSecrecy:是否需要前置加密,NO(允许加密,但不支持PFS:perfect forward secrecy),默认是YES
    • NSRequiresCertificateTransparency:是否需要有效的签名证书,YES(需要),默认是NO

    本文只是简单的介绍了一下如何配置ATS,及解决由于服务器不支持TLS1.2造成的https无法访问的问题,需要了解httpsTLS的具体工作流程,请参考相关资料。

    参考资料

    #iOS问题记录#关于NSURLSession/NSURLConnection HTTP load failed (kCFStreamErrorDomainSSL, -9801)

    iOS 9 适配系列教程

    iOS 9.0

    整理iOS9适配中出现的坑(图文)

    Cocoa Keys

    NSURLSession/NSURLConnection HTTP load failed (kCFStreamErrorDomainSSL, -9802) on a subdomain?

  • 相关阅读:
    RDLC报表开发技巧备忘
    C#3.0"扩展方法"简记
    将activity转化成view
    取消logcat输出
    低栏的项目切换
    android edittext 限制文本框输入的长度和提示信息
    android如何调用dotnet编写的webservice
    iphone 式退出
    几种tabhost的总结(1)
    切换浏览示意图
  • 原文地址:https://www.cnblogs.com/fishbay/p/7216142.html
Copyright © 2020-2023  润新知