精选文章

21. 安全与加密

2018-08-23 · 安全

21. 安全与加密

安全能力主要体现在三点:通信安全、数据安全、密钥管理。

一、ATS 与 HTTPS

iOS 默认要求 HTTPS,除非在 Info.plist 中显式配置例外。线上不要关闭 ATS。

二、证书校验(Pinning)

import Foundation

final class PinnedSessionDelegate: NSObject, URLSessionDelegate {
    private let pinnedData: Data

    init(pinnedCertData: Data) {
        self.pinnedData = pinnedCertData
    }

    func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge,
                    completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
        guard let serverTrust = challenge.protectionSpace.serverTrust,
              let cert = SecTrustGetCertificateAtIndex(serverTrust, 0) else {
            completionHandler(.cancelAuthenticationChallenge, nil)
            return
        }

        let serverData = SecCertificateCopyData(cert) as Data
        if serverData == pinnedData {
            completionHandler(.useCredential, URLCredential(trust: serverTrust))
        } else {
            completionHandler(.cancelAuthenticationChallenge, nil)
        }
    }
}

三、CryptoKit 哈希

import CryptoKit

func sha256(_ input: String) -> String {
    let data = Data(input.utf8)
    let hash = SHA256.hash(data: data)
    return hash.compactMap { String(format: "%02x", $0) }.joined()
}

四、HMAC 签名

import CryptoKit

func hmacSHA256(message: String, key: String) -> String {
    let keyData = SymmetricKey(data: Data(key.utf8))
    let signature = HMAC<SHA256>.authenticationCode(for: Data(message.utf8), using: keyData)
    return signature.map { String(format: "%02x", $0) }.joined()
}

五、敏感数据存储

敏感数据不要放 UserDefaults,必须用 Keychain。

import Security

func saveToken(_ token: Data) {
    let query: [String: Any] = [
        kSecClass as String: kSecClassGenericPassword,
        kSecAttrService as String: "token",
        kSecValueData as String: token
    ]
    SecItemDelete(query as CFDictionary)
    SecItemAdd(query as CFDictionary, nil)
}

安全不是一次性的功能,是长期能力:传输、存储、权限全部要一致。

JJ

作者简介

专注于内容创作、产品策略与设计实践。欢迎交流合作。

上一篇 下一篇