node_key.js 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. import { constants } from 'crypto';
  2. import getNamedCurve from './get_named_curve.js';
  3. import { JOSENotSupported } from '../util/errors.js';
  4. import checkModulusLength from './check_modulus_length.js';
  5. import { rsaPssParams } from './flags.js';
  6. const PSS = {
  7. padding: constants.RSA_PKCS1_PSS_PADDING,
  8. saltLength: constants.RSA_PSS_SALTLEN_DIGEST,
  9. };
  10. const ecCurveAlgMap = new Map([
  11. ['ES256', 'P-256'],
  12. ['ES256K', 'secp256k1'],
  13. ['ES384', 'P-384'],
  14. ['ES512', 'P-521'],
  15. ]);
  16. export default function keyForCrypto(alg, key) {
  17. switch (alg) {
  18. case 'EdDSA':
  19. if (!['ed25519', 'ed448'].includes(key.asymmetricKeyType)) {
  20. throw new TypeError('Invalid key for this operation, its asymmetricKeyType must be ed25519 or ed448');
  21. }
  22. return key;
  23. case 'RS256':
  24. case 'RS384':
  25. case 'RS512':
  26. if (key.asymmetricKeyType !== 'rsa') {
  27. throw new TypeError('Invalid key for this operation, its asymmetricKeyType must be rsa');
  28. }
  29. checkModulusLength(key, alg);
  30. return key;
  31. case rsaPssParams && 'PS256':
  32. case rsaPssParams && 'PS384':
  33. case rsaPssParams && 'PS512':
  34. if (key.asymmetricKeyType === 'rsa-pss') {
  35. const { hashAlgorithm, mgf1HashAlgorithm, saltLength } = key.asymmetricKeyDetails;
  36. const length = parseInt(alg.slice(-3), 10);
  37. if (hashAlgorithm !== undefined &&
  38. (hashAlgorithm !== `sha${length}` || mgf1HashAlgorithm !== hashAlgorithm)) {
  39. throw new TypeError(`Invalid key for this operation, its RSA-PSS parameters do not meet the requirements of "alg" ${alg}`);
  40. }
  41. if (saltLength !== undefined && saltLength > length >> 3) {
  42. throw new TypeError(`Invalid key for this operation, its RSA-PSS parameter saltLength does not meet the requirements of "alg" ${alg}`);
  43. }
  44. }
  45. else if (key.asymmetricKeyType !== 'rsa') {
  46. throw new TypeError('Invalid key for this operation, its asymmetricKeyType must be rsa or rsa-pss');
  47. }
  48. checkModulusLength(key, alg);
  49. return { key, ...PSS };
  50. case !rsaPssParams && 'PS256':
  51. case !rsaPssParams && 'PS384':
  52. case !rsaPssParams && 'PS512':
  53. if (key.asymmetricKeyType !== 'rsa') {
  54. throw new TypeError('Invalid key for this operation, its asymmetricKeyType must be rsa');
  55. }
  56. checkModulusLength(key, alg);
  57. return { key, ...PSS };
  58. case 'ES256':
  59. case 'ES256K':
  60. case 'ES384':
  61. case 'ES512': {
  62. if (key.asymmetricKeyType !== 'ec') {
  63. throw new TypeError('Invalid key for this operation, its asymmetricKeyType must be ec');
  64. }
  65. const actual = getNamedCurve(key);
  66. const expected = ecCurveAlgMap.get(alg);
  67. if (actual !== expected) {
  68. throw new TypeError(`Invalid key curve for the algorithm, its curve must be ${expected}, got ${actual}`);
  69. }
  70. return { dsaEncoding: 'ieee-p1363', key };
  71. }
  72. default:
  73. throw new JOSENotSupported(`alg ${alg} is not supported either by JOSE or your javascript runtime`);
  74. }
  75. }