我想通过swift中的rest call api传递pfx文件。存储在本地驱动器中的pfx文件。我将在python中完成,因此示例代码在
下面 var json=["{\"panInquiry\":{\"Header\":{\"TranID\":\"12345\",\"Corp_ID\":\"ZSA01\",\"Maker_ID\":\"\",\"Checker_ID\":\"\",\"Approver_ID\":\"\",\"Nsdl_UserID\":\"B3456789\"},\"Body\":{\"panNumbers\":[{\"pan1\":\"abba@123\"}]}}}"]
let jsonData = try? JSONSerialization.data(withJSONObject: json)
// create post request
let url=URL(string:"https://dshdjksdhsjhd")
// let pathToCert = Bundle.main.path(forResource: "mychatbot", ofType: "pfx")
// let localCertificate:NSData = NSData(contentsOfFile: pathToCert!)!
// var pemPath: String? = "/Users/rohitverma/Desktop/A/mychatbot.pfx"
var request = URLRequest(url: url!)
request.httpMethod = "POST"
let str="ZSA:pas@12345"
let utf8str = str.data(using: String.Encoding.utf8)
let base64Encoded = utf8str?.base64EncodedString(options: NSData.Base64EncodingOptions(rawValue: 0))
//print("Encoded: base64Encoded")
request.setValue("Basic \(base64Encoded)", forHTTPHeaderField: "Authorization")
// insert json data to the request
request.httpBody = jsonData
let task = URLSession.shared.dataTask(with: request) { data, response, error in
guard let data = data, error == nil else {
print(error?.localizedDescription ?? "No data")
return
}
let responseJSON = try? JSONSerialization.jsonObject(with: data, options: [])
if let responseJSON = responseJSON as? [String: Any] {
print(responseJSON)
}
}
task.resume()
}
}
这将是一个过程,但我不知道如何通过swift中的请求传递ssl证书。 在python中,它将通过以下代码
完成response = requests.post(url, json=json.loads(jsonstr, object_pairs_hook=OrderedDict),headers={"Authorization": "Basic %s" % b64Val},cert='C:\\Users\\lenovo\\Desktop\\mychatbot.pem', verify=True)
答案 0 :(得分:2)
您必须实施URLSessionDelegate
并执行以下操作:
static func getCertSession() -> URLSession {
let sessionDelegate = MySessionDelegate()
let conf = URLSessionConfiguration.default
conf.requestCachePolicy = NSURLRequest.CachePolicy.reloadIgnoringLocalCacheData
conf.timeoutIntervalForRequest = 1000
conf.timeoutIntervalForResource = 1000
return URLSession.init(configuration: conf, delegate: sessionDelegate, delegateQueue: OperationQueue.main)
}
class MySessionDelegate : NSObject : URLSessionDelegate {
public func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
if let localCertPath = Bundle.main.url(forResource: PATH_OF_YOUR_CERT, withExtension: "pfx"),
let localCertData = try? Data(contentsOf: localCertPath)
{
let identityAndTrust:IdentityAndTrust = extractIdentity(certData: localCertData as NSData, certPassword: PASSWORD_OF_YOUR_PFX)
if challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodClientCertificate {
let urlCredential:URLCredential = URLCredential(
identity: identityAndTrust.identityRef,
certificates: identityAndTrust.certArray as [AnyObject],
persistence: URLCredential.Persistence.forSession);
completionHandler(URLSession.AuthChallengeDisposition.useCredential, urlCredential);
return
}
}
challenge.sender?.cancel(challenge)
completionHandler(URLSession.AuthChallengeDisposition.rejectProtectionSpace, nil)
}
}
最后使用getCertSession().task(...)
代替URLSeesion.shared.task(...)
修改的
public struct IdentityAndTrust {
public var identityRef:SecIdentity
public var trust:SecTrust
public var certArray:NSArray
}
public func extractIdentity(certData:NSData, certPassword:String) -> IdentityAndTrust {
var identityAndTrust:IdentityAndTrust!
var securityError:OSStatus = errSecSuccess
var items: CFArray?
let certOptions: Dictionary = [ kSecImportExportPassphrase as String : certPassword ];
// import certificate to read its entries
securityError = SecPKCS12Import(certData, certOptions as CFDictionary, &items);
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> {
// grab the identity
let identityPointer:AnyObject? = certEntry["identity"];
let secIdentityRef:SecIdentity = identityPointer as! SecIdentity!;
// grab the trust
let trustPointer:AnyObject? = certEntry["trust"];
let trustRef:SecTrust = trustPointer as! SecTrust;
// grab the certificate chain
var certRef: SecCertificate?
SecIdentityCopyCertificate(secIdentityRef, &certRef);
let certArray:NSMutableArray = NSMutableArray();
certArray.add(certRef as SecCertificate!);
identityAndTrust = IdentityAndTrust(identityRef: secIdentityRef, trust: trustRef, certArray: certArray);
}
}
return identityAndTrust;
}
答案 1 :(得分:0)
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
@IBAction func pfxcl(_ sender: Any) {
print("Btn press")
var json=["{\"panInquiry\":{\"Header\":{\"TranID\":\"12345\",\"Corp_ID\":\"ASXE\",\"Maker_ID\":\"\",\"Checker_ID\":\"\",\"Approver_ID\":\"\",\"Nsdl_UserID\":\"ASFD454D\"},\"Body\":{\"panNumbers\":[{\"pan1\":\"qswerf98\"}]}}}"]
let jsonData = try? JSONSerialization.data(withJSONObject: json)
// create post request
let url=URL(string:"https://apideveloper.com")
var request = URLRequest(url: url!)
request.httpMethod = "POST"
let str="ACZZ:password@345"
let utf8str = str.data(using: String.Encoding.utf8)
let base64Encoded = utf8str?.base64EncodedString(options: NSData.Base64EncodingOptions(rawValue: 0))
//print("Encoded: base64Encoded")
request.setValue("Basic \(base64Encoded)", forHTTPHeaderField: "Authorization")
request.httpBody = jsonData
let task = URLSession.shared.dataTask(with: request) { data, response, error in
guard let data = data, error == nil else {
print(error?.localizedDescription ?? "No data")
return
}
let responseJSON = try? JSONSerialization.jsonObject(with: data, options: [])
if let responseJSON = responseJSON as? [String: Any] {
print(responseJSON)
}
}
task.resume()
class MySessionDelegate : NSObject , URLSessionDelegate {
func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
if let localCertPath = Bundle.main.url(forResource: "mychatbot", withExtension: "pfx"),
let localCertData = try? Data(contentsOf: localCertPath)
{
let identityAndTrust : IdentityAndTrust = extractIdentity(certData: localCertData as NSData, certPassword: "ACZZ:password@345")
if challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodClientCertificate {
let urlCredential:URLCredential = URLCredential(
identity: identityAndTrust.identityRef,
certificates: identityAndTrust.certArray as [AnyObject],
persistence: URLCredential.Persistence.forSession);
completionHandler(URLSession.AuthChallengeDisposition.useCredential, urlCredential);
return
}
}
challenge.sender?.cancel(challenge)
completionHandler(URLSession.AuthChallengeDisposition.rejectProtectionSpace, nil)
}
func getCertSession() -> URLSession {
let sessionDelegate = MySessionDelegate()
let conf = URLSessionConfiguration.default
conf.requestCachePolicy = NSURLRequest.CachePolicy.reloadIgnoringLocalCacheData
conf.timeoutIntervalForRequest = 1000
conf.timeoutIntervalForResource = 1000
return URLSession.init(configuration: conf, delegate: sessionDelegate as! URLSessionDelegate, delegateQueue: OperationQueue.main)
}
struct IdentityAndTrust {
public var identityRef:SecIdentity
public var trust:SecTrust
public var certArray:NSArray
}
func extractIdentity(certData:NSData, certPassword:String) -> IdentityAndTrust {
var identityAndTrust:IdentityAndTrust!
var securityError:OSStatus = errSecSuccess
var items: CFArray?
let certOptions: Dictionary = [ kSecImportExportPassphrase as String : certPassword ];
securityError = SecPKCS12Import(certData, certOptions as CFDictionary, &items);
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;
var certRef: SecCertificate?
SecIdentityCopyCertificate(secIdentityRef, &certRef);
let certArray:NSMutableArray = NSMutableArray();
certArray.add(certRef as SecCertificate!);
identityAndTrust = IdentityAndTrust(identityRef: secIdentityRef, trust: trustRef, certArray: certArray);
}
}
return identityAndTrust;
}
}
}
}