 
 extension String: Hashable {
 
-    public func digest(_ algorithm: Algorithm, key: String? = nil) -> String {
+    public func digest(_ algorithm: Algorithm) -> String {
+        return digest(algorithm, key: Optional<Data>.none)
+    }
+
+    public func digest(_ algorithm: Algorithm, key: String?) -> String {
+        return digest(algorithm, key: key?.data(using: .utf8))
+    }
+
+    public func digest(_ algorithm: Algorithm, key: Data?) -> String {
         let str = Array(self.utf8CString)
         let strLen = str.count-1
         let digestLen = algorithm.digestLength
         let result = UnsafeMutablePointer<UInt8>.allocate(capacity: digestLen)
 
         if let key = key {
-            let keyStr = Array(key.utf8CString)
-            let keyLen = keyStr.count-1
-            CCHmac(algorithm.hmacAlgorithm, keyStr, keyLen, str, strLen, result)
+            key.withUnsafeBytes { body in
+                CCHmac(algorithm.hmacAlgorithm, UnsafeRawPointer(body), key.count, str, count, result)
+            }
         } else {
             _ = algorithm.digestAlgorithm(str, CC_LONG(strLen), result)
         }


extension Data: Hashable {

    public func digest(_ algorithm: Algorithm, key: String? = nil) -> Data {
        let count = self.count
        let digestLen = algorithm.digestLength


            }

            if let key = key {
                key.withUnsafeBytes { body in
                    CCHmac(algorithm.hmacAlgorithm, UnsafeRawPointer(body), key.count, bytes, count, result)
                }
            } else {
                _ = algorithm.digestAlgorithm(bytes, CC_LONG(count), result)
            }
