1

I want to transform this JavaScript HMAC code to Swift using CryptoSwift library.

var crypto = require("crypto");
var currentDate = Moment.utc().format("YYYYMMDDHH");
var hmac = crypto.createHmac("sha256", "secretTokenKey123");
hmac.update(currentDate);
var code = hmac.digest("hex").toUpperCase();

What is the best way to do that?

This is what I tried, but did not return the correct code:

    let formatter = DateFormatter()
    formatter.dateFormat = "yyyyMMddHH"
    let dateString = formatter.string(from: Date())
    let baseString = secretToken + dateString
    print(baseString.sha256().uppercased())

I also tried this, but it returns the same wrong code

    var digest = SHA2(variant: .sha256)
    var bytes: Array<UInt8>?
    do {
        _ = try digest.update(withBytes: secretToken.bytes)
        _ = try digest.update(withBytes: dateString.bytes)
        bytes = try digest.finish()
    } catch {}
    if let result = bytes?.toHexString().uppercased() {
        print(result)
    }

I also tried to use HMCA from CryptoSwift directly. But I do not know what message I need to authenticate:

HMAC(key: secretToken.bytes, variant: .sha256).authenticate(???)
4
  • I tried to use try HMAC(key: key, variant: .sha256).authenticate(bytes) from CryptoSwift. However it does not match how it is used in my JS example. I do not have something to put in as bytes. Commented Dec 23, 2017 at 11:16
  • @Andreas I updated my question to show what I already tried without the correct result. Commented Dec 23, 2017 at 11:40
  • It is best to avoid using CryptoSwift, amoung other things it is 500 to 1000 times slower than Common Crypto based implementations. Apple's Common Crypto is FIPS certified and as such has been well vetted, using CryptoSwift is taking a chance on correctness and security. Commented Dec 23, 2017 at 13:01
  • @zaph Can you tell me how to implement this using Apple's Common Crypto? Commented Dec 28, 2017 at 10:58

2 Answers 2

2

I just discovered the solution myself:

HMAC(key: secretToken.bytes, variant: .sha256).authenticate(dateString.bytes).toHexString().uppercased()
Sign up to request clarification or add additional context in comments.

Comments

0

HAMC SHA256 in Common Crypto

func hmacSHA256(message:Data, key:Data) -> Data {
    var macData = Data(count: Int(CC_SHA256_DIGEST_LENGTH))

    macData.withUnsafeMutableBytes {macBytes in
        message.withUnsafeBytes {messageBytes in
            key.withUnsafeBytes {keyBytes in
                CCHmac(CCHmacAlgorithm(kCCHmacAlgSHA256),
                       keyBytes,     key.count,
                       messageBytes, message.count,
                       macBytes)
            }
        }
    }
    return macData
}

let clearData = "clearData0123456".data(using:.utf8)!
let keyData   = "keyData8901234562".data(using:.utf8)!
let hmacData  = hmacSHA256(message:clearData, key:keyData)
print("hmacData: \(String(describing: hmacData as NSData))")

hmacData: fcc487ce7dc1115a69a37dc3710610a87ad2fc9c85e2e0a52f0e7ee1dc9407c1

Note:
Include #import <CommonCrypto/CommonCrypto.h> in a bridging header.
Add Security.framework to the project

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.