访次: AmazingCounters.com 次

Alamofire + kingfisher Https 自签名证书

kingfisher 验证自签名证书下载HTTPS图片 

 let downer =

            KingfisherManager.shared.downloader

        downer.trustedHosts = Set(["主机地址"])

就是这么简单

Alamofire:

ServerTrustPolicy枚举中使用pinCertificates。 case pinCertificates(certificates: [SecCertificate], validateCertificateChain: Bool, validateHost: Bool) 传入自签名证书信息。 示例代码: let path = Bundle.main .path(forResource: "selfSigned_pubCA.cer", ofType: nil) let data = NSData(contentsOfFile: path!) let certificates :[SecCertificate] = [data as! SecCertificate] let policies : [String : ServerTrustPolicy] = ["172.16.88.230" : .pinCertificates(certificates: certificates, validateCertificateChain: true, validateHost: true)] 把这个 policies 作为参数传进manager 构造函数中即可  但是let certificates :[SecCertificate] = [data as! SecCertificate]但是在这里崩溃了,不能强转
下一个方案:

//定义一个结构体,存储认证相关信息

struct IdentityAndTrust {

    var identityRef:SecIdentity

    var trust:SecTrust

    var certArray:AnyObject

}

 

func customExtractIdentity() -> IdentityAndTrust {

    var identityAndTrust:IdentityAndTrust!

    var securityError:OSStatus = errSecSuccess

    let cerPath: String? = Bundle.main.path(forResource: "eidsp", ofType: "p12")!

    print("cerPath%@",cerPath as Any)

    let cerData = NSData(contentsOfFile:cerPath!)!

    print("cerData%@",cerData as Any)

    let key : NSString = kSecImportExportPassphrase as NSString

    let options : NSDictionary = [key : ""] //客户端证书密码

    var items : CFArray?

    securityError = SecPKCS12Import(cerData, options, &items)

    print("securityError%@",securityError)

    if securityError == errSecSuccess {

            let certItems:CFArray = items as CFArray!;

            let certItemsArray:Array = certItems as Array

            let dict:AnyObject? = certItemsArray.first;

            if let certEntry:Dictionary = dict as? Dictionary<String, AnyObject> {

            let identityPointer:AnyObject? = certEntry["identity"];

            let secIdentityRef:SecIdentity = identityPointer as! SecIdentity!

            let trustPointer:AnyObject? = certEntry["trust"]

            let trustRef:SecTrust = trustPointer as! SecTrust

            let chainPointer:AnyObject? = certEntry["chain"]

            identityAndTrust = IdentityAndTrust(identityRef: secIdentityRef,

                                                trust: trustRef, certArray:  chainPointer!)

        }

    }

    return identityAndTrust;

}

func httpsmanager(){

      manager?.delegate.sessionDidReceiveChallenge = { session, challenge in

print("challenge.protectionSpace.authenticationMethod!!!!!!!!!!!%@",challenge.protectionSpace.authenticationMethod)

        if challenge.protectionSpace.authenticationMethod

            == NSURLAuthenticationMethodServerTrust

        {   print("服务器认证!")

            let credential = URLCredential(trust: challenge.protectionSpace.serverTrust!)

            return (.useCredential, credential)

        }

        else if challenge.protectionSpace.authenticationMethod

            == NSURLAuthenticationMethodClientCertificate {

            print("客户端证书认证!")

            let identityAndTrust:IdentityAndTrust = customExtractIdentity();

            let urlCredential:URLCredential = URLCredential(

                identity: identityAndTrust.identityRef,

                certificates: identityAndTrust.certArray as? [AnyObject],

                persistence: URLCredential.Persistence.forSession);

            return (.useCredential, urlCredential);

        }

        else {

            print("其它情况(不接受认证)")

            return (.cancelAuthenticationChallenge, nil)

        }

    }

}

把httpsmanager()这个方法放在工具类里每次请求都调用一次就好了 我知道我这是个笨方法如果有搞好的方法请告知!   



挥毫泼墨,书写人生篇章
posted @ 2017-09-22 10:40  JusDoit  阅读(653)  评论(0编辑  收藏  举报