密钥和密钥规范(KeySpec)有什么区别?

15
在Java加密库中,有两种不同的密钥表示方式 - KeyKeySpec。文档暗示它们之间存在差异 - KeySpec是“透明”的(这意味着什么),但没有方法,而Key具有getEncoded方法。您应该使用KeyFactory在两者之间进行转换(确实有一个getKeySpec方法可供转换)。
然而,SecretKeySpec同时实现了KeyKeySpec!但是,还有一个名为SecretKeyFactory的类,它不继承自KeyFactory
所有这些已经让我彻底困惑了。一个“Key”和一个“KeySpec”有什么不同,以及“SecretKeySpec”和“SecretKeyFactory”是如何涉及其中的?
2个回答

5

“透明”在这里意味着所有实现/扩展KeySpec接口的类/接口都应以独立于提供程序的方式公开有关密钥的元数据。这些元数据实际上在密钥的常见用途(加密等)中从未被使用,但只有在需要查看密钥的数学属性时才会使用。了解有关密钥的此类独立于提供程序的数据可能很有用,例如,如果您想从/到字节流生成密钥、钩取驻留在HSM上的密钥,或者甚至找出密钥是否弱。

DESKeySpec.isWeak(byte[] key, int offset)

无论您想公开关于密钥的哪些元数据都取决于您。 KeySpec 只是一个标记接口(标记接口设计模式)。
与使用 KeySpec 进行可能的内省相反,使用 SecretKeyFactory 生成的密钥是“不透明的”,因为您无法获取有关密钥的完整数学(模数、指数、编码等)和其他元数据(例如上面的 DESKeySpec)。
另一方面,SecretKeySpec 是 JCE 的开箱即用解决方案,可从字节流生成密钥,因此它实现了 KeyKeySpec - 使用提供的 KeySpec 生成密钥,并使用 Key.getEncoded() 使密钥可用。

4
关键对象和关键规范(KeySpecs)是密钥数据的两种不同表示形式。
密码使用关键对象来初始化其加密算法,但是密钥可能需要转换为更便携的格式以进行传输或存储。
密钥的透明表示意味着您可以通过相应规范类中定义的其中一个get方法单独访问每个密钥材料值。
For example, DSAPrivateKeySpec defines getX, getP, getQ, and getG methods, to access the private key x, and the DSA algorithm parameters used to calculate the key(the prime p, the sub-prime q, and the base g). 

如果密钥储存在硬件设备上,其规范可能包含有助于在设备上识别密钥的信息。相比之下,此表示与Key接口定义的不透明表示形成对比,在不透明表示中,您无法直接访问密钥材料字段。换句话说,“不透明”表示仅为您提供了有限的密钥访问方式 - 只能使用Key接口定义的三种方法:getAlgorithm、getFormat和getEncoded。
可以按照特定于算法的方式或算法独立的编码格式(例如ASN.1)指定密钥。
For example, a DSA private key may be specified by its components x, p, q, and g (eg: DSAPrivateKeySpec), or it may be specified using its DER encoding (eg: PKCS8EncodedKeySpec).

KeyFactory类和SecretKeyFactory类可用于在密钥和KeySpec之间转换,即透明和不透明的密钥表示之间的转换。
参考和更多细节可在以下网址找到: https://docs.oracle.com/javase/8/docs/technotes/guides/security/crypto/CryptoSpec.html#KeySpecs

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接