本文介绍了带有自签名证书的 Alamofire/ServerTrustPolicy的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想使用 Alamofire 通过带有自签名证书的 https 连接与我的服务器进行通信.我的环境在本地主机上运行.我尝试连接,但响应一直是这样的:

I want to use Alamofire to communicate with my server over a https connection with a self signed certificate. My environment runs on localhost. I've tried to connect, but the response all the time looks like this:

Success: false
Response String: nil

我已经用以下代码完成了:

I've done it with the following code:

import Foundation
import UIKit
import Alamofire

class MessageView: UITableViewController {

    let defaultManager: Alamofire.Manager = {
        let serverTrustPolicies: [String: ServerTrustPolicy] = [
            "localhost": .DisableEvaluation
        ]

        let configuration = NSURLSessionConfiguration.defaultSessionConfiguration()
        configuration.HTTPAdditionalHeaders = Alamofire.Manager.defaultHTTPHeaders

        return Alamofire.Manager(
            configuration: configuration,
            serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies)
        )
    }()

    override func viewDidLoad() {
        super.viewDidLoad()

        defaultManager
            .request(.GET, "https://localhost:3443/message")
            .responseJSON { _, _, result in
                print("Success: (result.isSuccess)")
                print("Response String: (result.value)")
            }
    }

}

我已经用这行 bash 创建了服务器端证书:

I've created the server side certificates with this line of bash:

openssl req -x509 -nodes -days 999 -newkey rsa:2048 -keyout server.key -out server.crt

我不知道我做错了什么.帮助会很棒.

I don't know what am I doing wrong. Help would be great.

### 更新 ###

这是 cURL 请求.在我看来,没有问题,还是我错了?

Here is the cURL request. In my opinion, there is no problem, or am I wrong?

curl -X GET https://localhost:3443/message -k -v

*   Trying ::1...
* Connected to localhost (::1) port 3443 (#0)
* TLS 1.2 connection using TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384
* Server certificate: teawithfruit
> GET /message HTTP/1.1
> Host: localhost:3443
> User-Agent: curl/7.43.0
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: application/json; charset=utf-8
< Content-Length: 1073
< Date: Tue, 15 Sep 2015 06:20:45 GMT
< Connection: keep-alive
<
* Connection #0 to host localhost left intact

[{"_id":"55f3ed2d81a334558241e2f4","email":"[email protected]","password":"abc","name":"teawithfruit","language":"en","__v":0,"timestamp":1442049325159,"messages":[{"_id":"55f40553e568236589772c61","user":"55f3ed2d81a334558241e2f4","language":"en","message":"hello world","__v":0,"timestamp":1442055507301,"id":"55f40553e568236589772c61"},{"_id":"55f48b2b02e7b059b54e99f6","user":"55f3ed2d81a334558241e2f4","language":"en","message":"hello world","__v":0,"timestamp":1442089771312,"id":"55f48b2b02e7b059b54e99f6"}],"id":"55f3ed2d81a334558241e2f4"}]

### 更新 2 ###

抱歉回复晚了.这是两个调试打印:

Sorry for the late answer.Here are the two debugPrints:

请求调试打印:

$ curl -i
  -H "Accept-Language: en-US;q=1.0"
  -H "Accept-Encoding: gzip;q=1.0,compress;q=0.5"
  -H "User-Agent: Message/com.teawithfruit.Message (1; OS Version 9.0 (Build 13A340))"
  "https://localhost:3443/message"

结果调试打印:

FAILURE: Error Domain=NSURLErrorDomain Code=-999 "cancelled" UserInfo={NSErrorFailingURLKey=https://localhost:3443/message, NSLocalizedDescription=cancelled, NSErrorFailingURLStringKey=https://localhost:3443/message}

### 更新 3 ###

这是可能是 ATS 问题的完整错误?

Here is the complete error with maybe an ATS problem?

nil
$ curl -i
  -H "Accept-Language: en-US;q=1.0"
  -H "Accept-Encoding: gzip;q=1.0,compress;q=0.5"
  -H "User-Agent: Message/com.teawithfruit.Message (1; OS Version 9.0 (Build 13A340))"
  "https://localhost:3443/message"
2015-10-17 15:10:48.346 Message[25531:1001269] NSURLSession/NSURLConnection HTTP load failed (kCFStreamErrorDomainSSL, -9802)
FAILURE: Error Domain=NSURLErrorDomain Code=-1200 "An SSL error has occurred and a secure connection to the server cannot be made." UserInfo={NSURLErrorFailingURLPeerTrustErrorKey=<SecTrustRef: 0x7fdc3044b740>, NSLocalizedRecoverySuggestion=Would you like to connect to the server anyway?, _kCFStreamErrorDomainKey=3, _kCFStreamErrorCodeKey=-9802, NSErrorPeerCertificateChainKey=<CFArray 0x7fdc2a7ca300 [0x10f7037b0]>{type = immutable, count = 1, values = (
  0 : <cert(0x7fdc31d31670) s: teawithfruit i: teawithfruit>
)}, NSUnderlyingError=0x7fdc30064bd0 {Error Domain=kCFErrorDomainCFNetwork Code=-1200 "(null)" UserInfo={_kCFStreamPropertySSLClientCertificateState=0, kCFStreamPropertySSLPeerTrust=<SecTrustRef: 0x7fdc3044b740>, _kCFNetworkCFStreamSSLErrorOriginalValue=-9802, _kCFStreamErrorDomainKey=3, _kCFStreamErrorCodeKey=-9802, kCFStreamPropertySSLPeerCertificates=<CFArray 0x7fdc2a7ca300 [0x10f7037b0]>{type = immutable, count = 1, values = (
  0 : <cert(0x7fdc31d31670) s: teawithfruit i: teawithfruit>
)}}}, NSLocalizedDescription=An SSL error has occurred and a secure connection to the server cannot be made., NSErrorFailingURLKey=https://localhost:3443/message, NSErrorFailingURLStringKey=https://localhost:3443/message, NSErrorClientCertificateStateKey=0}
Success: false
Response String: nil

推荐答案

您需要在创建 ServerTrustPolicy 字典时添加 port 域.

You need to add the port domain when you create your ServerTrustPolicy dictionary.

let defaultManager: Alamofire.Manager = {
    let serverTrustPolicies: [String: ServerTrustPolicy] = [
        "localhost:3443": .DisableEvaluation
    ]

    let configuration = NSURLSessionConfiguration.defaultSessionConfiguration()
    configuration.HTTPAdditionalHeaders = Alamofire.Manager.defaultHTTPHeaders

    return Alamofire.Manager(
        configuration: configuration,
        serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies)
    )
}()

这篇关于带有自签名证书的 Alamofire/ServerTrustPolicy的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-03 21:09