jose 4.1.5 → 4.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -1
- package/dist/browser/index.js +1 -0
- package/dist/browser/jwe/flattened/encrypt.js +15 -4
- package/dist/browser/jwe/general/decrypt.js +3 -0
- package/dist/browser/jwe/general/encrypt.js +171 -0
- package/dist/browser/jwks/remote.js +16 -12
- package/dist/browser/jws/general/sign.js +25 -29
- package/dist/browser/lib/cek.js +5 -6
- package/dist/browser/lib/decrypt_key_management.js +1 -1
- package/dist/browser/lib/encrypt_key_management.js +1 -1
- package/dist/browser/lib/iv.js +4 -11
- package/dist/browser/runtime/aeskw.js +2 -1
- package/dist/browser/runtime/asn1.js +2 -1
- package/dist/browser/runtime/decrypt.js +2 -1
- package/dist/browser/runtime/ecdhes.js +5 -4
- package/dist/browser/runtime/encrypt.js +2 -1
- package/dist/browser/runtime/get_sign_verify_key.js +3 -2
- package/dist/browser/runtime/key_to_jwk.js +2 -1
- package/dist/browser/runtime/pbes2kw.js +2 -1
- package/dist/browser/runtime/rsaes.js +3 -2
- package/dist/node/cjs/index.js +9 -7
- package/dist/node/cjs/jwe/flattened/encrypt.js +16 -5
- package/dist/node/cjs/jwe/general/decrypt.js +3 -0
- package/dist/node/cjs/jwe/general/encrypt.js +175 -0
- package/dist/node/cjs/jwks/remote.js +16 -12
- package/dist/node/cjs/jws/general/sign.js +25 -29
- package/dist/node/cjs/lib/cek.js +5 -6
- package/dist/node/cjs/lib/decrypt_key_management.js +1 -1
- package/dist/node/cjs/lib/encrypt_key_management.js +1 -1
- package/dist/node/cjs/lib/iv.js +4 -11
- package/dist/node/cjs/runtime/aeskw.js +4 -3
- package/dist/node/cjs/runtime/asn1.js +2 -1
- package/dist/node/cjs/runtime/decrypt.js +5 -4
- package/dist/node/cjs/runtime/ecdhes.js +5 -4
- package/dist/node/cjs/runtime/encrypt.js +5 -4
- package/dist/node/cjs/runtime/get_named_curve.js +2 -1
- package/dist/node/cjs/runtime/get_sign_verify_key.js +3 -2
- package/dist/node/cjs/runtime/key_to_jwk.js +2 -1
- package/dist/node/cjs/runtime/pbes2kw.js +2 -1
- package/dist/node/cjs/runtime/rsaes.js +4 -3
- package/dist/node/esm/index.js +1 -0
- package/dist/node/esm/jwe/flattened/encrypt.js +15 -4
- package/dist/node/esm/jwe/general/decrypt.js +3 -0
- package/dist/node/esm/jwe/general/encrypt.js +171 -0
- package/dist/node/esm/jwks/remote.js +16 -12
- package/dist/node/esm/jws/general/sign.js +25 -29
- package/dist/node/esm/lib/cek.js +5 -6
- package/dist/node/esm/lib/decrypt_key_management.js +1 -1
- package/dist/node/esm/lib/encrypt_key_management.js +1 -1
- package/dist/node/esm/lib/iv.js +4 -11
- package/dist/node/esm/runtime/aeskw.js +4 -3
- package/dist/node/esm/runtime/asn1.js +2 -1
- package/dist/node/esm/runtime/decrypt.js +5 -4
- package/dist/node/esm/runtime/ecdhes.js +5 -4
- package/dist/node/esm/runtime/encrypt.js +5 -4
- package/dist/node/esm/runtime/get_named_curve.js +2 -1
- package/dist/node/esm/runtime/get_sign_verify_key.js +3 -2
- package/dist/node/esm/runtime/key_to_jwk.js +2 -1
- package/dist/node/esm/runtime/pbes2kw.js +2 -1
- package/dist/node/esm/runtime/rsaes.js +4 -3
- package/dist/types/index.d.ts +3 -1
- package/dist/types/jwe/compact/decrypt.d.ts +2 -2
- package/dist/types/jwe/compact/encrypt.d.ts +2 -2
- package/dist/types/jwe/flattened/encrypt.d.ts +1 -0
- package/dist/types/jwe/general/encrypt.d.ts +20 -0
- package/dist/types/jws/compact/sign.d.ts +2 -2
- package/dist/types/jws/compact/verify.d.ts +2 -2
- package/dist/types/jws/general/sign.d.ts +3 -0
- package/dist/types/jwt/decrypt.d.ts +2 -2
- package/dist/types/jwt/encrypt.d.ts +2 -2
- package/dist/types/jwt/sign.d.ts +2 -2
- package/dist/types/jwt/verify.d.ts +2 -2
- package/dist/types/types.d.ts +17 -14
- package/package.json +1 -1
|
@@ -4,9 +4,10 @@ import crypto, { isCryptoKey } from './webcrypto.js';
|
|
|
4
4
|
import { checkEncCryptoKey } from '../lib/crypto_key.js';
|
|
5
5
|
import checkKeyLength from './check_key_length.js';
|
|
6
6
|
import invalidKeyInput from '../lib/invalid_key_input.js';
|
|
7
|
+
import { types } from './is_key_like.js';
|
|
7
8
|
export const encrypt = async (alg, key, cek) => {
|
|
8
9
|
if (!isCryptoKey(key)) {
|
|
9
|
-
throw new TypeError(invalidKeyInput(key,
|
|
10
|
+
throw new TypeError(invalidKeyInput(key, ...types));
|
|
10
11
|
}
|
|
11
12
|
checkEncCryptoKey(key, alg, 'encrypt', 'wrapKey');
|
|
12
13
|
checkKeyLength(alg, key);
|
|
@@ -21,7 +22,7 @@ export const encrypt = async (alg, key, cek) => {
|
|
|
21
22
|
};
|
|
22
23
|
export const decrypt = async (alg, key, encryptedKey) => {
|
|
23
24
|
if (!isCryptoKey(key)) {
|
|
24
|
-
throw new TypeError(invalidKeyInput(key,
|
|
25
|
+
throw new TypeError(invalidKeyInput(key, ...types));
|
|
25
26
|
}
|
|
26
27
|
checkEncCryptoKey(key, alg, 'decrypt', 'unwrapKey');
|
|
27
28
|
checkKeyLength(alg, key);
|
package/dist/node/cjs/index.js
CHANGED
|
@@ -1,12 +1,14 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.base64url = exports.generateSecret = exports.generateKeyPair = exports.errors = exports.decodeProtectedHeader = exports.importJWK = exports.importX509 = exports.importPKCS8 = exports.importSPKI = exports.exportJWK = exports.exportSPKI = exports.exportPKCS8 = exports.UnsecuredJWT = exports.createRemoteJWKSet = exports.EmbeddedJWK = exports.calculateJwkThumbprint = exports.EncryptJWT = exports.SignJWT = exports.GeneralSign = exports.FlattenedSign = exports.CompactSign = exports.FlattenedEncrypt = exports.CompactEncrypt = exports.jwtDecrypt = exports.jwtVerify = exports.generalVerify = exports.flattenedVerify = exports.compactVerify = exports.generalDecrypt = exports.flattenedDecrypt = exports.compactDecrypt = void 0;
|
|
3
|
+
exports.base64url = exports.generateSecret = exports.generateKeyPair = exports.errors = exports.decodeProtectedHeader = exports.importJWK = exports.importX509 = exports.importPKCS8 = exports.importSPKI = exports.exportJWK = exports.exportSPKI = exports.exportPKCS8 = exports.UnsecuredJWT = exports.createRemoteJWKSet = exports.EmbeddedJWK = exports.calculateJwkThumbprint = exports.EncryptJWT = exports.SignJWT = exports.GeneralSign = exports.FlattenedSign = exports.CompactSign = exports.FlattenedEncrypt = exports.CompactEncrypt = exports.jwtDecrypt = exports.jwtVerify = exports.generalVerify = exports.flattenedVerify = exports.compactVerify = exports.GeneralEncrypt = exports.generalDecrypt = exports.flattenedDecrypt = exports.compactDecrypt = void 0;
|
|
4
4
|
var decrypt_js_1 = require("./jwe/compact/decrypt.js");
|
|
5
5
|
Object.defineProperty(exports, "compactDecrypt", { enumerable: true, get: function () { return decrypt_js_1.compactDecrypt; } });
|
|
6
6
|
var decrypt_js_2 = require("./jwe/flattened/decrypt.js");
|
|
7
7
|
Object.defineProperty(exports, "flattenedDecrypt", { enumerable: true, get: function () { return decrypt_js_2.flattenedDecrypt; } });
|
|
8
8
|
var decrypt_js_3 = require("./jwe/general/decrypt.js");
|
|
9
9
|
Object.defineProperty(exports, "generalDecrypt", { enumerable: true, get: function () { return decrypt_js_3.generalDecrypt; } });
|
|
10
|
+
var encrypt_js_1 = require("./jwe/general/encrypt.js");
|
|
11
|
+
Object.defineProperty(exports, "GeneralEncrypt", { enumerable: true, get: function () { return encrypt_js_1.GeneralEncrypt; } });
|
|
10
12
|
var verify_js_1 = require("./jws/compact/verify.js");
|
|
11
13
|
Object.defineProperty(exports, "compactVerify", { enumerable: true, get: function () { return verify_js_1.compactVerify; } });
|
|
12
14
|
var verify_js_2 = require("./jws/flattened/verify.js");
|
|
@@ -17,10 +19,10 @@ var verify_js_4 = require("./jwt/verify.js");
|
|
|
17
19
|
Object.defineProperty(exports, "jwtVerify", { enumerable: true, get: function () { return verify_js_4.jwtVerify; } });
|
|
18
20
|
var decrypt_js_4 = require("./jwt/decrypt.js");
|
|
19
21
|
Object.defineProperty(exports, "jwtDecrypt", { enumerable: true, get: function () { return decrypt_js_4.jwtDecrypt; } });
|
|
20
|
-
var
|
|
21
|
-
Object.defineProperty(exports, "CompactEncrypt", { enumerable: true, get: function () { return
|
|
22
|
-
var
|
|
23
|
-
Object.defineProperty(exports, "FlattenedEncrypt", { enumerable: true, get: function () { return
|
|
22
|
+
var encrypt_js_2 = require("./jwe/compact/encrypt.js");
|
|
23
|
+
Object.defineProperty(exports, "CompactEncrypt", { enumerable: true, get: function () { return encrypt_js_2.CompactEncrypt; } });
|
|
24
|
+
var encrypt_js_3 = require("./jwe/flattened/encrypt.js");
|
|
25
|
+
Object.defineProperty(exports, "FlattenedEncrypt", { enumerable: true, get: function () { return encrypt_js_3.FlattenedEncrypt; } });
|
|
24
26
|
var sign_js_1 = require("./jws/compact/sign.js");
|
|
25
27
|
Object.defineProperty(exports, "CompactSign", { enumerable: true, get: function () { return sign_js_1.CompactSign; } });
|
|
26
28
|
var sign_js_2 = require("./jws/flattened/sign.js");
|
|
@@ -29,8 +31,8 @@ var sign_js_3 = require("./jws/general/sign.js");
|
|
|
29
31
|
Object.defineProperty(exports, "GeneralSign", { enumerable: true, get: function () { return sign_js_3.GeneralSign; } });
|
|
30
32
|
var sign_js_4 = require("./jwt/sign.js");
|
|
31
33
|
Object.defineProperty(exports, "SignJWT", { enumerable: true, get: function () { return sign_js_4.SignJWT; } });
|
|
32
|
-
var
|
|
33
|
-
Object.defineProperty(exports, "EncryptJWT", { enumerable: true, get: function () { return
|
|
34
|
+
var encrypt_js_4 = require("./jwt/encrypt.js");
|
|
35
|
+
Object.defineProperty(exports, "EncryptJWT", { enumerable: true, get: function () { return encrypt_js_4.EncryptJWT; } });
|
|
34
36
|
var thumbprint_js_1 = require("./jwk/thumbprint.js");
|
|
35
37
|
Object.defineProperty(exports, "calculateJwkThumbprint", { enumerable: true, get: function () { return thumbprint_js_1.calculateJwkThumbprint; } });
|
|
36
38
|
var embedded_js_1 = require("./jwk/embedded.js");
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.FlattenedEncrypt = void 0;
|
|
3
|
+
exports.FlattenedEncrypt = exports.unprotected = void 0;
|
|
4
4
|
const base64url_js_1 = require("../../runtime/base64url.js");
|
|
5
5
|
const encrypt_js_1 = require("../../runtime/encrypt.js");
|
|
6
6
|
const zlib_js_1 = require("../../runtime/zlib.js");
|
|
@@ -10,6 +10,7 @@ const errors_js_1 = require("../../util/errors.js");
|
|
|
10
10
|
const is_disjoint_js_1 = require("../../lib/is_disjoint.js");
|
|
11
11
|
const buffer_utils_js_1 = require("../../lib/buffer_utils.js");
|
|
12
12
|
const validate_crit_js_1 = require("../../lib/validate_crit.js");
|
|
13
|
+
exports.unprotected = Symbol();
|
|
13
14
|
class FlattenedEncrypt {
|
|
14
15
|
constructor(plaintext) {
|
|
15
16
|
if (!(plaintext instanceof Uint8Array)) {
|
|
@@ -68,7 +69,7 @@ class FlattenedEncrypt {
|
|
|
68
69
|
throw new errors_js_1.JWEInvalid('either setProtectedHeader, setUnprotectedHeader, or sharedUnprotectedHeader must be called before #encrypt()');
|
|
69
70
|
}
|
|
70
71
|
if (!(0, is_disjoint_js_1.default)(this._protectedHeader, this._unprotectedHeader, this._sharedUnprotectedHeader)) {
|
|
71
|
-
throw new errors_js_1.JWEInvalid('JWE
|
|
72
|
+
throw new errors_js_1.JWEInvalid('JWE Protected, JWE Shared Unprotected and JWE Per-Recipient Header Parameter names must be disjoint');
|
|
72
73
|
}
|
|
73
74
|
const joseHeader = {
|
|
74
75
|
...this._protectedHeader,
|
|
@@ -107,11 +108,21 @@ class FlattenedEncrypt {
|
|
|
107
108
|
let parameters;
|
|
108
109
|
({ cek, encryptedKey, parameters } = await (0, encrypt_key_management_js_1.default)(alg, enc, key, this._cek, this._keyManagementParameters));
|
|
109
110
|
if (parameters) {
|
|
110
|
-
if (
|
|
111
|
-
this.
|
|
111
|
+
if (options && exports.unprotected in options) {
|
|
112
|
+
if (!this._unprotectedHeader) {
|
|
113
|
+
this.setUnprotectedHeader(parameters);
|
|
114
|
+
}
|
|
115
|
+
else {
|
|
116
|
+
this._unprotectedHeader = { ...this._unprotectedHeader, ...parameters };
|
|
117
|
+
}
|
|
112
118
|
}
|
|
113
119
|
else {
|
|
114
|
-
this._protectedHeader
|
|
120
|
+
if (!this._protectedHeader) {
|
|
121
|
+
this.setProtectedHeader(parameters);
|
|
122
|
+
}
|
|
123
|
+
else {
|
|
124
|
+
this._protectedHeader = { ...this._protectedHeader, ...parameters };
|
|
125
|
+
}
|
|
115
126
|
}
|
|
116
127
|
}
|
|
117
128
|
}
|
|
@@ -11,6 +11,9 @@ async function generalDecrypt(jwe, key, options) {
|
|
|
11
11
|
if (!Array.isArray(jwe.recipients) || !jwe.recipients.every(is_object_js_1.default)) {
|
|
12
12
|
throw new errors_js_1.JWEInvalid('JWE Recipients missing or incorrect type');
|
|
13
13
|
}
|
|
14
|
+
if (!jwe.recipients.length) {
|
|
15
|
+
throw new errors_js_1.JWEInvalid('JWE Recipients has no members');
|
|
16
|
+
}
|
|
14
17
|
for (const recipient of jwe.recipients) {
|
|
15
18
|
try {
|
|
16
19
|
return await (0, decrypt_js_1.flattenedDecrypt)({
|
|
@@ -0,0 +1,175 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.GeneralEncrypt = void 0;
|
|
4
|
+
const encrypt_js_1 = require("../flattened/encrypt.js");
|
|
5
|
+
const errors_js_1 = require("../../util/errors.js");
|
|
6
|
+
const cek_js_1 = require("../../lib/cek.js");
|
|
7
|
+
const is_disjoint_js_1 = require("../../lib/is_disjoint.js");
|
|
8
|
+
const encrypt_key_management_js_1 = require("../../lib/encrypt_key_management.js");
|
|
9
|
+
const base64url_js_1 = require("../../runtime/base64url.js");
|
|
10
|
+
const validate_crit_js_1 = require("../../lib/validate_crit.js");
|
|
11
|
+
class IndividualRecipient {
|
|
12
|
+
constructor(enc, key, options) {
|
|
13
|
+
this.parent = enc;
|
|
14
|
+
this.key = key;
|
|
15
|
+
this.options = options;
|
|
16
|
+
}
|
|
17
|
+
setUnprotectedHeader(unprotectedHeader) {
|
|
18
|
+
if (this.unprotectedHeader) {
|
|
19
|
+
throw new TypeError('setUnprotectedHeader can only be called once');
|
|
20
|
+
}
|
|
21
|
+
this.unprotectedHeader = unprotectedHeader;
|
|
22
|
+
return this;
|
|
23
|
+
}
|
|
24
|
+
addRecipient(...args) {
|
|
25
|
+
return this.parent.addRecipient(...args);
|
|
26
|
+
}
|
|
27
|
+
encrypt(...args) {
|
|
28
|
+
return this.parent.encrypt(...args);
|
|
29
|
+
}
|
|
30
|
+
done() {
|
|
31
|
+
return this.parent;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
class GeneralEncrypt {
|
|
35
|
+
constructor(plaintext) {
|
|
36
|
+
this._recipients = [];
|
|
37
|
+
this._plaintext = plaintext;
|
|
38
|
+
}
|
|
39
|
+
addRecipient(key, options) {
|
|
40
|
+
const recipient = new IndividualRecipient(this, key, { crit: options === null || options === void 0 ? void 0 : options.crit });
|
|
41
|
+
this._recipients.push(recipient);
|
|
42
|
+
return recipient;
|
|
43
|
+
}
|
|
44
|
+
setProtectedHeader(protectedHeader) {
|
|
45
|
+
if (this._protectedHeader) {
|
|
46
|
+
throw new TypeError('setProtectedHeader can only be called once');
|
|
47
|
+
}
|
|
48
|
+
this._protectedHeader = protectedHeader;
|
|
49
|
+
return this;
|
|
50
|
+
}
|
|
51
|
+
setSharedUnprotectedHeader(sharedUnprotectedHeader) {
|
|
52
|
+
if (this._unprotectedHeader) {
|
|
53
|
+
throw new TypeError('setSharedUnprotectedHeader can only be called once');
|
|
54
|
+
}
|
|
55
|
+
this._unprotectedHeader = sharedUnprotectedHeader;
|
|
56
|
+
return this;
|
|
57
|
+
}
|
|
58
|
+
setAdditionalAuthenticatedData(aad) {
|
|
59
|
+
this._aad = aad;
|
|
60
|
+
return this;
|
|
61
|
+
}
|
|
62
|
+
async encrypt(options) {
|
|
63
|
+
var _a, _b, _c;
|
|
64
|
+
if (!this._recipients.length) {
|
|
65
|
+
throw new errors_js_1.JWEInvalid('at least one recipient must be added');
|
|
66
|
+
}
|
|
67
|
+
options = { deflateRaw: options === null || options === void 0 ? void 0 : options.deflateRaw };
|
|
68
|
+
if (this._recipients.length === 1) {
|
|
69
|
+
const [recipient] = this._recipients;
|
|
70
|
+
const flattened = await new encrypt_js_1.FlattenedEncrypt(this._plaintext)
|
|
71
|
+
.setAdditionalAuthenticatedData(this._aad)
|
|
72
|
+
.setProtectedHeader(this._protectedHeader)
|
|
73
|
+
.setSharedUnprotectedHeader(this._unprotectedHeader)
|
|
74
|
+
.setUnprotectedHeader(recipient.unprotectedHeader)
|
|
75
|
+
.encrypt(recipient.key, { ...recipient.options, ...options });
|
|
76
|
+
let jwe = {
|
|
77
|
+
ciphertext: flattened.ciphertext,
|
|
78
|
+
iv: flattened.iv,
|
|
79
|
+
recipients: [{}],
|
|
80
|
+
tag: flattened.tag,
|
|
81
|
+
};
|
|
82
|
+
if (flattened.aad)
|
|
83
|
+
jwe.aad = flattened.aad;
|
|
84
|
+
if (flattened.protected)
|
|
85
|
+
jwe.protected = flattened.protected;
|
|
86
|
+
if (flattened.unprotected)
|
|
87
|
+
jwe.unprotected = flattened.unprotected;
|
|
88
|
+
if (flattened.encrypted_key)
|
|
89
|
+
jwe.recipients[0].encrypted_key = flattened.encrypted_key;
|
|
90
|
+
if (flattened.header)
|
|
91
|
+
jwe.recipients[0].header = flattened.header;
|
|
92
|
+
return jwe;
|
|
93
|
+
}
|
|
94
|
+
let enc;
|
|
95
|
+
for (let i = 0; i < this._recipients.length; i++) {
|
|
96
|
+
const recipient = this._recipients[i];
|
|
97
|
+
if (!(0, is_disjoint_js_1.default)(this._protectedHeader, this._unprotectedHeader, recipient.unprotectedHeader)) {
|
|
98
|
+
throw new errors_js_1.JWEInvalid('JWE Protected, JWE Shared Unprotected and JWE Per-Recipient Header Parameter names must be disjoint');
|
|
99
|
+
}
|
|
100
|
+
const joseHeader = {
|
|
101
|
+
...this._protectedHeader,
|
|
102
|
+
...this._unprotectedHeader,
|
|
103
|
+
...recipient.unprotectedHeader,
|
|
104
|
+
};
|
|
105
|
+
const { alg } = joseHeader;
|
|
106
|
+
if (typeof alg !== 'string' || !alg) {
|
|
107
|
+
throw new errors_js_1.JWEInvalid('JWE "alg" (Algorithm) Header Parameter missing or invalid');
|
|
108
|
+
}
|
|
109
|
+
if (alg === 'dir' || alg === 'ECDH-ES') {
|
|
110
|
+
throw new errors_js_1.JWEInvalid('"dir" and "ECDH-ES" alg may only be used with a single recipient');
|
|
111
|
+
}
|
|
112
|
+
if (typeof joseHeader.enc !== 'string' || !joseHeader.enc) {
|
|
113
|
+
throw new errors_js_1.JWEInvalid('JWE "enc" (Encryption Algorithm) Header Parameter missing or invalid');
|
|
114
|
+
}
|
|
115
|
+
if (!enc) {
|
|
116
|
+
enc = joseHeader.enc;
|
|
117
|
+
}
|
|
118
|
+
else if (enc !== joseHeader.enc) {
|
|
119
|
+
throw new errors_js_1.JWEInvalid('JWE "enc" (Encryption Algorithm) Header Parameter must be the same for all recipients');
|
|
120
|
+
}
|
|
121
|
+
(0, validate_crit_js_1.default)(errors_js_1.JWEInvalid, new Map(), recipient.options.crit, this._protectedHeader, joseHeader);
|
|
122
|
+
if (joseHeader.zip !== undefined) {
|
|
123
|
+
if (!this._protectedHeader || !this._protectedHeader.zip) {
|
|
124
|
+
throw new errors_js_1.JWEInvalid('JWE "zip" (Compression Algorithm) Header MUST be integrity protected');
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
const cek = (0, cek_js_1.default)(enc);
|
|
129
|
+
let jwe = {
|
|
130
|
+
ciphertext: '',
|
|
131
|
+
iv: '',
|
|
132
|
+
recipients: [],
|
|
133
|
+
tag: '',
|
|
134
|
+
};
|
|
135
|
+
for (let i = 0; i < this._recipients.length; i++) {
|
|
136
|
+
const recipient = this._recipients[i];
|
|
137
|
+
const target = {};
|
|
138
|
+
jwe.recipients.push(target);
|
|
139
|
+
if (i === 0) {
|
|
140
|
+
const flattened = await new encrypt_js_1.FlattenedEncrypt(this._plaintext)
|
|
141
|
+
.setAdditionalAuthenticatedData(this._aad)
|
|
142
|
+
.setContentEncryptionKey(cek)
|
|
143
|
+
.setProtectedHeader(this._protectedHeader)
|
|
144
|
+
.setSharedUnprotectedHeader(this._unprotectedHeader)
|
|
145
|
+
.setUnprotectedHeader(recipient.unprotectedHeader)
|
|
146
|
+
.encrypt(recipient.key, {
|
|
147
|
+
...recipient.options,
|
|
148
|
+
...options,
|
|
149
|
+
[encrypt_js_1.unprotected]: true,
|
|
150
|
+
});
|
|
151
|
+
jwe.ciphertext = flattened.ciphertext;
|
|
152
|
+
jwe.iv = flattened.iv;
|
|
153
|
+
jwe.tag = flattened.tag;
|
|
154
|
+
if (flattened.aad)
|
|
155
|
+
jwe.aad = flattened.aad;
|
|
156
|
+
if (flattened.protected)
|
|
157
|
+
jwe.protected = flattened.protected;
|
|
158
|
+
if (flattened.unprotected)
|
|
159
|
+
jwe.unprotected = flattened.unprotected;
|
|
160
|
+
target.encrypted_key = flattened.encrypted_key;
|
|
161
|
+
if (flattened.header)
|
|
162
|
+
target.header = flattened.header;
|
|
163
|
+
continue;
|
|
164
|
+
}
|
|
165
|
+
const { encryptedKey, parameters } = await (0, encrypt_key_management_js_1.default)(((_a = recipient.unprotectedHeader) === null || _a === void 0 ? void 0 : _a.alg) ||
|
|
166
|
+
((_b = this._protectedHeader) === null || _b === void 0 ? void 0 : _b.alg) ||
|
|
167
|
+
((_c = this._unprotectedHeader) === null || _c === void 0 ? void 0 : _c.alg), enc, recipient.key, cek);
|
|
168
|
+
target.encrypted_key = (0, base64url_js_1.encode)(encryptedKey);
|
|
169
|
+
if (recipient.unprotectedHeader || parameters)
|
|
170
|
+
target.header = { ...recipient.unprotectedHeader, ...parameters };
|
|
171
|
+
}
|
|
172
|
+
return jwe;
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
exports.GeneralEncrypt = GeneralEncrypt;
|
|
@@ -40,17 +40,21 @@ class RemoteJWKSet {
|
|
|
40
40
|
}
|
|
41
41
|
return Date.now() < this._cooldownStarted + this._cooldownDuration;
|
|
42
42
|
}
|
|
43
|
-
async getKey(protectedHeader) {
|
|
43
|
+
async getKey(protectedHeader, token) {
|
|
44
|
+
const joseHeader = {
|
|
45
|
+
...protectedHeader,
|
|
46
|
+
...token.header,
|
|
47
|
+
};
|
|
44
48
|
if (!this._jwks) {
|
|
45
49
|
await this.reload();
|
|
46
50
|
}
|
|
47
51
|
const candidates = this._jwks.keys.filter((jwk) => {
|
|
48
|
-
let candidate = jwk.kty === getKtyFromAlg(
|
|
49
|
-
if (candidate && typeof
|
|
50
|
-
candidate =
|
|
52
|
+
let candidate = jwk.kty === getKtyFromAlg(joseHeader.alg);
|
|
53
|
+
if (candidate && typeof joseHeader.kid === 'string') {
|
|
54
|
+
candidate = joseHeader.kid === jwk.kid;
|
|
51
55
|
}
|
|
52
56
|
if (candidate && typeof jwk.alg === 'string') {
|
|
53
|
-
candidate =
|
|
57
|
+
candidate = joseHeader.alg === jwk.alg;
|
|
54
58
|
}
|
|
55
59
|
if (candidate && typeof jwk.use === 'string') {
|
|
56
60
|
candidate = jwk.use === 'sig';
|
|
@@ -58,11 +62,11 @@ class RemoteJWKSet {
|
|
|
58
62
|
if (candidate && Array.isArray(jwk.key_ops)) {
|
|
59
63
|
candidate = jwk.key_ops.includes('verify');
|
|
60
64
|
}
|
|
61
|
-
if (candidate &&
|
|
65
|
+
if (candidate && joseHeader.alg === 'EdDSA') {
|
|
62
66
|
candidate = jwk.crv === 'Ed25519' || jwk.crv === 'Ed448';
|
|
63
67
|
}
|
|
64
68
|
if (candidate) {
|
|
65
|
-
switch (
|
|
69
|
+
switch (joseHeader.alg) {
|
|
66
70
|
case 'ES256':
|
|
67
71
|
candidate = jwk.crv === 'P-256';
|
|
68
72
|
break;
|
|
@@ -84,7 +88,7 @@ class RemoteJWKSet {
|
|
|
84
88
|
if (length === 0) {
|
|
85
89
|
if (this.coolingDown() === false) {
|
|
86
90
|
await this.reload();
|
|
87
|
-
return this.getKey(protectedHeader);
|
|
91
|
+
return this.getKey(protectedHeader, token);
|
|
88
92
|
}
|
|
89
93
|
throw new errors_js_1.JWKSNoMatchingKey();
|
|
90
94
|
}
|
|
@@ -92,14 +96,14 @@ class RemoteJWKSet {
|
|
|
92
96
|
throw new errors_js_1.JWKSMultipleMatchingKeys();
|
|
93
97
|
}
|
|
94
98
|
const cached = this._cached.get(jwk) || this._cached.set(jwk, {}).get(jwk);
|
|
95
|
-
if (cached[
|
|
96
|
-
const keyObject = await (0, import_js_1.importJWK)({ ...jwk, ext: true },
|
|
99
|
+
if (cached[joseHeader.alg] === undefined) {
|
|
100
|
+
const keyObject = await (0, import_js_1.importJWK)({ ...jwk, ext: true }, joseHeader.alg);
|
|
97
101
|
if (keyObject instanceof Uint8Array || keyObject.type !== 'public') {
|
|
98
102
|
throw new errors_js_1.JWKSInvalid('JSON Web Key Set members must be public keys');
|
|
99
103
|
}
|
|
100
|
-
cached[
|
|
104
|
+
cached[joseHeader.alg] = keyObject;
|
|
101
105
|
}
|
|
102
|
-
return cached[
|
|
106
|
+
return cached[joseHeader.alg];
|
|
103
107
|
}
|
|
104
108
|
async reload() {
|
|
105
109
|
if (!this._pendingFetch) {
|
|
@@ -3,33 +3,34 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.GeneralSign = void 0;
|
|
4
4
|
const sign_js_1 = require("../flattened/sign.js");
|
|
5
5
|
const errors_js_1 = require("../../util/errors.js");
|
|
6
|
-
const signatureRef = new WeakMap();
|
|
7
6
|
class IndividualSignature {
|
|
7
|
+
constructor(sig, key, options) {
|
|
8
|
+
this.parent = sig;
|
|
9
|
+
this.key = key;
|
|
10
|
+
this.options = options;
|
|
11
|
+
}
|
|
8
12
|
setProtectedHeader(protectedHeader) {
|
|
9
|
-
if (this.
|
|
13
|
+
if (this.protectedHeader) {
|
|
10
14
|
throw new TypeError('setProtectedHeader can only be called once');
|
|
11
15
|
}
|
|
12
|
-
this.
|
|
16
|
+
this.protectedHeader = protectedHeader;
|
|
13
17
|
return this;
|
|
14
18
|
}
|
|
15
19
|
setUnprotectedHeader(unprotectedHeader) {
|
|
16
|
-
if (this.
|
|
20
|
+
if (this.unprotectedHeader) {
|
|
17
21
|
throw new TypeError('setUnprotectedHeader can only be called once');
|
|
18
22
|
}
|
|
19
|
-
this.
|
|
23
|
+
this.unprotectedHeader = unprotectedHeader;
|
|
20
24
|
return this;
|
|
21
25
|
}
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
}
|
|
25
|
-
get _protectedHeader() {
|
|
26
|
-
return signatureRef.get(this).protectedHeader;
|
|
26
|
+
addSignature(...args) {
|
|
27
|
+
return this.parent.addSignature(...args);
|
|
27
28
|
}
|
|
28
|
-
|
|
29
|
-
|
|
29
|
+
sign(...args) {
|
|
30
|
+
return this.parent.sign(...args);
|
|
30
31
|
}
|
|
31
|
-
|
|
32
|
-
return
|
|
32
|
+
done() {
|
|
33
|
+
return this.parent;
|
|
33
34
|
}
|
|
34
35
|
}
|
|
35
36
|
class GeneralSign {
|
|
@@ -38,8 +39,7 @@ class GeneralSign {
|
|
|
38
39
|
this._payload = payload;
|
|
39
40
|
}
|
|
40
41
|
addSignature(key, options) {
|
|
41
|
-
const signature = new IndividualSignature();
|
|
42
|
-
signatureRef.set(signature, { key, options });
|
|
42
|
+
const signature = new IndividualSignature(this, key, options);
|
|
43
43
|
this._signatures.push(signature);
|
|
44
44
|
return signature;
|
|
45
45
|
}
|
|
@@ -51,23 +51,19 @@ class GeneralSign {
|
|
|
51
51
|
signatures: [],
|
|
52
52
|
payload: '',
|
|
53
53
|
};
|
|
54
|
-
let
|
|
55
|
-
|
|
56
|
-
const { protectedHeader, unprotectedHeader, options, key } = signatureRef.get(sig);
|
|
54
|
+
for (let i = 0; i < this._signatures.length; i++) {
|
|
55
|
+
const signature = this._signatures[i];
|
|
57
56
|
const flattened = new sign_js_1.FlattenedSign(this._payload);
|
|
58
|
-
|
|
59
|
-
|
|
57
|
+
flattened.setProtectedHeader(signature.protectedHeader);
|
|
58
|
+
flattened.setUnprotectedHeader(signature.unprotectedHeader);
|
|
59
|
+
const { payload, ...rest } = await flattened.sign(signature.key, signature.options);
|
|
60
|
+
if (i === 0) {
|
|
61
|
+
jws.payload = payload;
|
|
60
62
|
}
|
|
61
|
-
if (
|
|
62
|
-
|
|
63
|
+
else if (jws.payload !== payload) {
|
|
64
|
+
throw new errors_js_1.JWSInvalid('inconsistent use of JWS Unencoded Payload Option (RFC7797)');
|
|
63
65
|
}
|
|
64
|
-
const { payload, ...rest } = await flattened.sign(key, options);
|
|
65
|
-
payloads.add(payload);
|
|
66
|
-
jws.payload = payload;
|
|
67
66
|
jws.signatures.push(rest);
|
|
68
|
-
}));
|
|
69
|
-
if (payloads.size !== 1) {
|
|
70
|
-
throw new errors_js_1.JWSInvalid('inconsistent use of JWS Unencoded Payload Option (RFC7797)');
|
|
71
67
|
}
|
|
72
68
|
return jws;
|
|
73
69
|
}
|
package/dist/node/cjs/lib/cek.js
CHANGED
|
@@ -5,18 +5,17 @@ const errors_js_1 = require("../util/errors.js");
|
|
|
5
5
|
const random_js_1 = require("../runtime/random.js");
|
|
6
6
|
function bitLength(alg) {
|
|
7
7
|
switch (alg) {
|
|
8
|
-
case 'A128CBC-HS256':
|
|
9
|
-
return 256;
|
|
10
|
-
case 'A192CBC-HS384':
|
|
11
|
-
return 384;
|
|
12
|
-
case 'A256CBC-HS512':
|
|
13
|
-
return 512;
|
|
14
8
|
case 'A128GCM':
|
|
15
9
|
return 128;
|
|
16
10
|
case 'A192GCM':
|
|
17
11
|
return 192;
|
|
18
12
|
case 'A256GCM':
|
|
13
|
+
case 'A128CBC-HS256':
|
|
19
14
|
return 256;
|
|
15
|
+
case 'A192CBC-HS384':
|
|
16
|
+
return 384;
|
|
17
|
+
case 'A256CBC-HS512':
|
|
18
|
+
return 512;
|
|
20
19
|
default:
|
|
21
20
|
throw new errors_js_1.JOSENotSupported(`Unsupported JWE Algorithm: ${alg}`);
|
|
22
21
|
}
|
|
@@ -42,7 +42,7 @@ async function decryptKeyManagement(alg, key, encryptedKey, joseHeader) {
|
|
|
42
42
|
throw new errors_js_1.JWEInvalid(`JOSE Header "apv" (Agreement PartyVInfo) invalid`);
|
|
43
43
|
partyVInfo = (0, base64url_js_1.decode)(joseHeader.apv);
|
|
44
44
|
}
|
|
45
|
-
const sharedSecret = await ECDH.deriveKey(epk, key, alg === 'ECDH-ES' ? joseHeader.enc : alg,
|
|
45
|
+
const sharedSecret = await ECDH.deriveKey(epk, key, alg === 'ECDH-ES' ? joseHeader.enc : alg, alg === 'ECDH-ES' ? (0, cek_js_1.bitLength)(joseHeader.enc) : parseInt(alg.substr(-5, 3), 10), partyUInfo, partyVInfo);
|
|
46
46
|
if (alg === 'ECDH-ES')
|
|
47
47
|
return sharedSecret;
|
|
48
48
|
if (encryptedKey === undefined)
|
|
@@ -31,7 +31,7 @@ async function encryptKeyManagement(alg, enc, key, providedCek, providedParamete
|
|
|
31
31
|
let { epk: ephemeralKey } = providedParameters;
|
|
32
32
|
ephemeralKey || (ephemeralKey = await ECDH.generateEpk(key));
|
|
33
33
|
const { x, y, crv, kty } = await (0, export_js_1.exportJWK)(ephemeralKey);
|
|
34
|
-
const sharedSecret = await ECDH.deriveKey(key, ephemeralKey, alg === 'ECDH-ES' ? enc : alg, parseInt(alg.substr(-5, 3), 10)
|
|
34
|
+
const sharedSecret = await ECDH.deriveKey(key, ephemeralKey, alg === 'ECDH-ES' ? enc : alg, alg === 'ECDH-ES' ? (0, cek_js_1.bitLength)(enc) : parseInt(alg.substr(-5, 3), 10), apu, apv);
|
|
35
35
|
parameters = { epk: { x, y, crv, kty } };
|
|
36
36
|
if (apu)
|
|
37
37
|
parameters.apu = (0, base64url_js_1.encode)(apu);
|
package/dist/node/cjs/lib/iv.js
CHANGED
|
@@ -5,24 +5,17 @@ const errors_js_1 = require("../util/errors.js");
|
|
|
5
5
|
const random_js_1 = require("../runtime/random.js");
|
|
6
6
|
function bitLength(alg) {
|
|
7
7
|
switch (alg) {
|
|
8
|
-
case 'A128CBC-HS256':
|
|
9
|
-
return 128;
|
|
10
8
|
case 'A128GCM':
|
|
11
|
-
return 96;
|
|
12
9
|
case 'A128GCMKW':
|
|
13
|
-
return 96;
|
|
14
|
-
case 'A192CBC-HS384':
|
|
15
|
-
return 128;
|
|
16
10
|
case 'A192GCM':
|
|
17
|
-
return 96;
|
|
18
11
|
case 'A192GCMKW':
|
|
19
|
-
return 96;
|
|
20
|
-
case 'A256CBC-HS512':
|
|
21
|
-
return 128;
|
|
22
12
|
case 'A256GCM':
|
|
23
|
-
return 96;
|
|
24
13
|
case 'A256GCMKW':
|
|
25
14
|
return 96;
|
|
15
|
+
case 'A128CBC-HS256':
|
|
16
|
+
case 'A192CBC-HS384':
|
|
17
|
+
case 'A256CBC-HS512':
|
|
18
|
+
return 128;
|
|
26
19
|
default:
|
|
27
20
|
throw new errors_js_1.JOSENotSupported(`Unsupported JWE Algorithm: ${alg}`);
|
|
28
21
|
}
|
|
@@ -11,6 +11,7 @@ const crypto_key_js_1 = require("../lib/crypto_key.js");
|
|
|
11
11
|
const is_key_object_js_1 = require("./is_key_object.js");
|
|
12
12
|
const invalid_key_input_js_1 = require("../lib/invalid_key_input.js");
|
|
13
13
|
const ciphers_js_1 = require("./ciphers.js");
|
|
14
|
+
const is_key_like_js_1 = require("./is_key_like.js");
|
|
14
15
|
function checkKeySize(key, alg) {
|
|
15
16
|
if (key.symmetricKeySize << 3 !== parseInt(alg.substr(1, 3), 10)) {
|
|
16
17
|
throw new TypeError(`Invalid key size for alg: ${alg}`);
|
|
@@ -27,9 +28,9 @@ function ensureKeyObject(key, alg, usage) {
|
|
|
27
28
|
(0, crypto_key_js_1.checkEncCryptoKey)(key, alg, usage);
|
|
28
29
|
return crypto_1.KeyObject.from(key);
|
|
29
30
|
}
|
|
30
|
-
throw new TypeError((0, invalid_key_input_js_1.default)(key,
|
|
31
|
+
throw new TypeError((0, invalid_key_input_js_1.default)(key, ...is_key_like_js_1.types, 'Uint8Array'));
|
|
31
32
|
}
|
|
32
|
-
const wrap =
|
|
33
|
+
const wrap = (alg, key, cek) => {
|
|
33
34
|
const size = parseInt(alg.substr(1, 3), 10);
|
|
34
35
|
const algorithm = `aes${size}-wrap`;
|
|
35
36
|
if (!(0, ciphers_js_1.default)(algorithm)) {
|
|
@@ -41,7 +42,7 @@ const wrap = async (alg, key, cek) => {
|
|
|
41
42
|
return (0, buffer_utils_js_1.concat)(cipher.update(cek), cipher.final());
|
|
42
43
|
};
|
|
43
44
|
exports.wrap = wrap;
|
|
44
|
-
const unwrap =
|
|
45
|
+
const unwrap = (alg, key, encryptedKey) => {
|
|
45
46
|
const size = parseInt(alg.substr(1, 3), 10);
|
|
46
47
|
const algorithm = `aes${size}-wrap`;
|
|
47
48
|
if (!(0, ciphers_js_1.default)(algorithm)) {
|
|
@@ -6,6 +6,7 @@ const buffer_1 = require("buffer");
|
|
|
6
6
|
const webcrypto_js_1 = require("./webcrypto.js");
|
|
7
7
|
const is_key_object_js_1 = require("./is_key_object.js");
|
|
8
8
|
const invalid_key_input_js_1 = require("../lib/invalid_key_input.js");
|
|
9
|
+
const is_key_like_js_1 = require("./is_key_like.js");
|
|
9
10
|
const genericExport = (keyType, keyFormat, key) => {
|
|
10
11
|
let keyObject;
|
|
11
12
|
if ((0, webcrypto_js_1.isCryptoKey)(key)) {
|
|
@@ -18,7 +19,7 @@ const genericExport = (keyType, keyFormat, key) => {
|
|
|
18
19
|
keyObject = key;
|
|
19
20
|
}
|
|
20
21
|
else {
|
|
21
|
-
throw new TypeError((0, invalid_key_input_js_1.default)(key,
|
|
22
|
+
throw new TypeError((0, invalid_key_input_js_1.default)(key, ...is_key_like_js_1.types));
|
|
22
23
|
}
|
|
23
24
|
if (keyObject.type !== keyType) {
|
|
24
25
|
throw new TypeError(`key is not a ${keyType} key`);
|
|
@@ -12,7 +12,8 @@ const crypto_key_js_1 = require("../lib/crypto_key.js");
|
|
|
12
12
|
const is_key_object_js_1 = require("./is_key_object.js");
|
|
13
13
|
const invalid_key_input_js_1 = require("../lib/invalid_key_input.js");
|
|
14
14
|
const ciphers_js_1 = require("./ciphers.js");
|
|
15
|
-
|
|
15
|
+
const is_key_like_js_1 = require("./is_key_like.js");
|
|
16
|
+
function cbcDecrypt(enc, cek, ciphertext, iv, tag, aad) {
|
|
16
17
|
const keySize = parseInt(enc.substr(1, 3), 10);
|
|
17
18
|
if ((0, is_key_object_js_1.default)(cek)) {
|
|
18
19
|
cek = cek.export();
|
|
@@ -46,7 +47,7 @@ async function cbcDecrypt(enc, cek, ciphertext, iv, tag, aad) {
|
|
|
46
47
|
}
|
|
47
48
|
return plaintext;
|
|
48
49
|
}
|
|
49
|
-
|
|
50
|
+
function gcmDecrypt(enc, cek, ciphertext, iv, tag, aad) {
|
|
50
51
|
const keySize = parseInt(enc.substr(1, 3), 10);
|
|
51
52
|
const algorithm = `aes-${keySize}-gcm`;
|
|
52
53
|
if (!(0, ciphers_js_1.default)(algorithm)) {
|
|
@@ -66,7 +67,7 @@ async function gcmDecrypt(enc, cek, ciphertext, iv, tag, aad) {
|
|
|
66
67
|
throw new errors_js_1.JWEDecryptionFailed();
|
|
67
68
|
}
|
|
68
69
|
}
|
|
69
|
-
const decrypt =
|
|
70
|
+
const decrypt = (enc, cek, ciphertext, iv, tag, aad) => {
|
|
70
71
|
let key;
|
|
71
72
|
if ((0, webcrypto_js_1.isCryptoKey)(cek)) {
|
|
72
73
|
(0, crypto_key_js_1.checkEncCryptoKey)(cek, enc, 'decrypt');
|
|
@@ -76,7 +77,7 @@ const decrypt = async (enc, cek, ciphertext, iv, tag, aad) => {
|
|
|
76
77
|
key = cek;
|
|
77
78
|
}
|
|
78
79
|
else {
|
|
79
|
-
throw new TypeError((0, invalid_key_input_js_1.default)(cek,
|
|
80
|
+
throw new TypeError((0, invalid_key_input_js_1.default)(cek, ...is_key_like_js_1.types, 'Uint8Array'));
|
|
80
81
|
}
|
|
81
82
|
(0, check_cek_length_js_1.default)(enc, key);
|
|
82
83
|
(0, check_iv_length_js_1.default)(enc, iv);
|