【发布时间】:2014-07-07 16:03:18
【问题描述】:
我正在尝试用 Swift 编写一个 HMAC 类,首先用 Objective C 编写它,然后使用 Bridging-Header 使该类可用于我的 Swift 代码。如果我粘贴了太多代码,我很抱歉,但我想了解为什么会发生这种情况,以便更好地理解 Swift 和 Objective C 的接口,以及如何解决我遇到的错误。 “TBGHMAC.calculateWithAlgorithm: forKey: and Data:”函数会产生“致命错误:无法解开 Optional.None”错误。
从顶部开始,这里是我的 Swift 代码中调用 Swift 代码的 sn-p
let key : String = "" // start with empty string"
let data : String = "" // start with empty string"
let signature : String = TBGHMAC.calculateWithAlgorithm(HMACAlgorithm.SHA256, forKey: key, andData: data)
println(signature)
这里是 TBGHMAC 头文件
#import <Foundation/Foundation.h>
#import <CommonCrypto/CommonCrypto.h>
@interface TBGHMAC : NSObject
typedef NS_ENUM(NSInteger, HMACAlgorithm)
{
SHA1,
MD5,
SHA256,
SHA384,
SHA512,
SHA224
};
+ (NSString *)calculateWithAlgorithm:(HMACAlgorithm)algorithm forKey:(NSString*)key andData:(NSString *)data;
+ (NSInteger)digestLengthForAlgorithm:(HMACAlgorithm)algorithm;
@end
最后是实现文件
+ (NSString *)calculateWithAlgorithm:(HMACAlgorithm)algorithm forKey:(NSString *)key andData:(NSString *)data
{
NSUInteger keyNumberOfBytes = [key lengthOfBytesUsingEncoding:NSUTF8StringEncoding];
void *keyBuffer = malloc(keyNumberOfBytes);
NSUInteger keyUsedLength = 0;
NSRange keyRange = NSMakeRange(0, [key length]);
BOOL keyResult = [key getBytes:keyBuffer maxLength:keyNumberOfBytes usedLength:&keyUsedLength encoding:NSUTF8StringEncoding options:0 range:keyRange remainingRange:NULL];
NSUInteger dataNumberOfBytes = [data lengthOfBytesUsingEncoding:NSUnicodeStringEncoding];
void *dataBuffer = malloc(dataNumberOfBytes);
NSUInteger dataUsedLength = 0;
NSRange dataRange = NSMakeRange(0, [data length]);
BOOL dataResult = [data getBytes:dataBuffer maxLength:dataNumberOfBytes usedLength:&dataUsedLength encoding:NSUTF8StringEncoding options:0 range:dataRange remainingRange:NULL];
NSInteger digestLength = [self digestLengthForAlgorithm:algorithm];
unsigned char hmac[digestLength];
CCHmac(algorithm, &keyBuffer, strlen(keyBuffer), &dataBuffer, strlen(dataBuffer), &hmac);
NSData *hmacBytes = [NSData dataWithBytes:hmac length:sizeof(hmac)];
NSString* returnStr = [[NSString alloc] initWithData:hmacBytes encoding:NSUTF8StringEncoding];
free(keyBuffer);
free(dataBuffer);
return returnStr;
}
+ (NSInteger)digestLengthForAlgorithm:(HMACAlgorithm)algorithm
{
switch (algorithm)
{
case MD5: return CC_MD5_DIGEST_LENGTH;
case SHA1: return CC_SHA1_DIGEST_LENGTH;
case SHA224: return CC_SHA224_DIGEST_LENGTH;
case SHA256: return CC_SHA256_DIGEST_LENGTH;
case SHA384: return CC_SHA384_DIGEST_LENGTH;
case SHA512: return CC_SHA512_DIGEST_LENGTH;
default: return 0;
}
}
@end
请指出为什么会出现此错误,以及如何解决。我不明白这个错误是如何产生的,因为我没有使用任何 Optionals,Xcode 也没有试图纠正我使用 Optionals。
【问题讨论】:
-
从 ObjC 传递到 Swift 的所有内容都是可选的,阅读有关如何在 Swift 中使用 ObjC 的文档可能会有所帮助:developer.apple.com/library/prerelease/ios/documentation/Swift/…