How to connect to self signed servers using Alamofire 1.3

前端 未结 5 1059
隐瞒了意图╮
隐瞒了意图╮ 2020-12-08 10:52

I get the below error while connecting to self signed server.

Error Domain=NSURLErrorDomain Code=-1202 \"The certificate for this server is invalid. You might be co

相关标签:
5条回答
  • 2020-12-08 11:24

    Another approach for my project. The ServerTrustPolicyManager is an open class, and it's serverTrustPolicy function is open too. So it can be override.

    // For Swift 3 and Alamofire 4.0
    open class MyServerTrustPolicyManager: ServerTrustPolicyManager {
    
        // Override this function in order to trust any self-signed https
        open override func serverTrustPolicy(forHost host: String) -> ServerTrustPolicy? {
            return ServerTrustPolicy.disableEvaluation
    
            // or, if `host` contains substring, return `disableEvaluation`
            // Ex: host contains `my_company.com`, then trust it.
        }
    }
    

    Then,

        let trustPolicies = MyServerTrustPolicyManager(policies: [:])
        let manager = Alamofire.SessionManager(configuration: sessionConfig, delegate: SessionDelegate(), serverTrustPolicyManager: trustPolicies)
    

    UPDATE @2018,01

    In order to trigger the ServerTrustPolicyManager, the project's Info.plist needs to be configured. I found the solution, detail at this post, cnoon's comment @ 1 Nov 2015.

    For example, if there are urls named site1.foo.com, site2.foo.com, .... Then add App Transport Security Settings -> Exception Domains -> foo.com dictionary, with following entries.

    • NSExceptionRequiresForwardSecrecy : NO
    • NSExceptionAllowsInsecureHTTPLoads : YES
    • NSIncludesSubdomains : YES

    More detail you can refer the post.

    0 讨论(0)
  • 2020-12-08 11:26

    An example is posted right in the README demonstrating exactly how to disable evaluation if you need to do so.

    Since you are going to need to create your own Manager instance as well, you'll want to do something like the following:

    class NetworkManager {
        static let sharedInstance = NetworkManager()
    
        let defaultManager: Alamofire.Manager = {
            let serverTrustPolicies: [String: ServerTrustPolicy] = [
                "test.example.com": .PinCertificates(
                    certificates: ServerTrustPolicy.certificatesInBundle(),
                    validateCertificateChain: true,
                    validateHost: true
                ),
                "insecure.expired-apis.com": .DisableEvaluation
            ]
    
            let configuration = NSURLSessionConfiguration.defaultSessionConfiguration()
            configuration.HTTPAdditionalHeaders = Alamofire.Manager.defaultHTTPHeaders
    
            return Alamofire.Manager(
                configuration: configuration,
                serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies)
            )
        }()
    }
    

    This will then allow you to make requests with the NetworkManager.sharedInstance.defaultManager object.

    0 讨论(0)
  • 2020-12-08 11:35

    Manager configuration for Swift 3 or Swift 4 and Alamofire 4:

    private static var manager: Alamofire.SessionManager = {
    
        // Create the server trust policies
        let serverTrustPolicies: [String: ServerTrustPolicy] = [
            "test.example.com": .disableEvaluation
        ]
    
        // Create custom manager
        let configuration = URLSessionConfiguration.default
        configuration.httpAdditionalHeaders = Alamofire.SessionManager.defaultHTTPHeaders
        let manager = Alamofire.SessionManager(
            configuration: URLSessionConfiguration.default,
            serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies)
        )
    
        return manager
    }()
    
    0 讨论(0)
  • 2020-12-08 11:41

    Anyway, the answer of @cnoon almost full. But I met another trouble of the ssl validation, so I want to put my code here if someone can get help from it.The manager init as:

    private var manager: Manager?
    // Import the certificates like xxx.cer to your project(anywhere will be fine), then the ServerTrustPolicy.certificatesInBundle() can find them
    let serverTrustPolicy = ServerTrustPolicy.PinCertificates(
                certificates: ServerTrustPolicy.certificatesInBundle(),
                validateCertificateChain: false,
                validateHost: true
            )
    let serverTrustPolicies: [String : ServerTrustPolicy] = [
                "sub.server.com": .DisableEvaluation, // because the certificates only add the main domain, so disable evaluation for subdomain
                "192.168.0.2:8090": .DisableEvaluation, // the IP address for request data
                "www.server.com": serverTrustPolicy
            ]
    manager = Manager(serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies))
    

    Then use the manager to request:

    // this function in the class which for manager the Alamofire request
    public func request(method: Alamofire.Method, _ URLString: URLStringConvertible,
                            parameters: [String : AnyObject]?) -> Alamofire.Request
        {
            // we do not need use Alamofire.request now, just use the manager you have initialized
            return manager!.request(method, URLString, parameters: parameters,
                                     headers: ["tokenId": UserManager_Inst.tokenID])
        }
    

    p.s.: it is the swift 2.3 sample

    0 讨论(0)
  • 2020-12-08 11:47

    There is a way to change the Server Trust Policy of the Alamofire manager shared instance, but it's not recommended. Instead you should create your own customised instance of the manager. Here is the recommended solution, code is Swift 2.0 with Alamofire from swift-2.0 branch, compiled in Xcode7 beta 5.

    Creating customised instance of the manager

    Because you will not use the request method on the Alamofire, but use the one on your custom manager instead, you need to think of where to store the manager. What I do is to store it as static in my networking wrapper (the class that utilizes Alamofire and deals with my application networking needs). I set it up like this:

    private static var Manager : Alamofire.Manager = {
            // Create the server trust policies
            let serverTrustPolicies: [String: ServerTrustPolicy] = [
                "maskeddomain.com": .DisableEvaluation
            ]
            // Create custom manager
            let configuration = NSURLSessionConfiguration.defaultSessionConfiguration()
            configuration.HTTPAdditionalHeaders = Alamofire.Manager.defaultHTTPHeaders
            let man = Alamofire.Manager(
                configuration: NSURLSessionConfiguration.defaultSessionConfiguration(),
                serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies)
            )
            return man
        }()
    

    Next step is to switch all your calls that use Alamofire.request() with Manager.request(), so you should have something like this:

    Manager.request(.GET, "http://stackoverflow.com").responseJSON(
        completionHandler: { (_, respose, result) -> Void in
                if result.isSuccess {
                    // enjoy your success
                } else if result.isFailure {
                    // deal with your failure
                }
        })
    

    If you want to change the shared instance of the manager anyway, go here for more info.

    0 讨论(0)
提交回复
热议问题