@bitgo/passkey-crypto 0.2.0 → 0.3.1
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/dist/src/attachPasskeyToWallet.d.ts +11 -0
- package/dist/src/attachPasskeyToWallet.d.ts.map +1 -0
- package/dist/src/attachPasskeyToWallet.js +63 -0
- package/dist/src/base64url.d.ts +16 -0
- package/dist/src/base64url.d.ts.map +1 -0
- package/dist/src/base64url.js +27 -0
- package/dist/src/deriveEnterpriseSalt.d.ts +7 -1
- package/dist/src/deriveEnterpriseSalt.d.ts.map +1 -1
- package/dist/src/deriveEnterpriseSalt.js +12 -42
- package/dist/src/derivePasskeyPrfKey.d.ts +15 -0
- package/dist/src/derivePasskeyPrfKey.d.ts.map +1 -0
- package/dist/src/derivePasskeyPrfKey.js +68 -0
- package/dist/src/index.d.ts +5 -0
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +12 -2
- package/dist/src/prfHelpers.d.ts.map +1 -1
- package/dist/src/prfHelpers.js +19 -4
- package/dist/src/registerPasskey.d.ts +10 -0
- package/dist/src/registerPasskey.d.ts.map +1 -0
- package/dist/src/registerPasskey.js +93 -0
- package/dist/src/removePasskeyFromAccount.d.ts +11 -0
- package/dist/src/removePasskeyFromAccount.d.ts.map +1 -0
- package/dist/src/removePasskeyFromAccount.js +15 -0
- package/dist/src/removePasskeyFromWallet.d.ts +10 -0
- package/dist/src/removePasskeyFromWallet.d.ts.map +1 -0
- package/dist/src/removePasskeyFromWallet.js +22 -0
- package/dist/test/integration/helpers/fixtures.d.ts +12 -0
- package/dist/test/integration/helpers/fixtures.d.ts.map +1 -0
- package/dist/test/integration/helpers/fixtures.js +15 -0
- package/dist/test/integration/helpers/mockBitGo.d.ts +27 -0
- package/dist/test/integration/helpers/mockBitGo.d.ts.map +1 -0
- package/dist/test/integration/helpers/mockBitGo.js +148 -0
- package/dist/test/integration/helpers/mockProvider.d.ts +5 -0
- package/dist/test/integration/helpers/mockProvider.d.ts.map +1 -0
- package/dist/test/integration/helpers/mockProvider.js +37 -0
- package/dist/test/integration/passkeyLifecycle.test.d.ts +2 -0
- package/dist/test/integration/passkeyLifecycle.test.d.ts.map +1 -0
- package/dist/test/integration/passkeyLifecycle.test.js +153 -0
- package/dist/test/unit/attachPasskeyToWallet.test.d.ts +2 -0
- package/dist/test/unit/attachPasskeyToWallet.test.d.ts.map +1 -0
- package/dist/test/unit/attachPasskeyToWallet.test.js +205 -0
- package/dist/test/unit/base64url.test.d.ts +2 -0
- package/dist/test/unit/base64url.test.d.ts.map +1 -0
- package/dist/test/unit/base64url.test.js +75 -0
- package/dist/test/unit/deriveEnterpriseSalt.test.js +8 -4
- package/dist/test/unit/derivePasskeyPrfKey.test.d.ts +2 -0
- package/dist/test/unit/derivePasskeyPrfKey.test.d.ts.map +1 -0
- package/dist/test/unit/derivePasskeyPrfKey.test.js +152 -0
- package/dist/test/unit/registerPasskey.test.d.ts +2 -0
- package/dist/test/unit/registerPasskey.test.d.ts.map +1 -0
- package/dist/test/unit/registerPasskey.test.js +155 -0
- package/dist/test/unit/removePasskeyFromAccount.test.d.ts +2 -0
- package/dist/test/unit/removePasskeyFromAccount.test.d.ts.map +1 -0
- package/dist/test/unit/removePasskeyFromAccount.test.js +88 -0
- package/dist/test/unit/removePasskeyFromWallet.test.d.ts +2 -0
- package/dist/test/unit/removePasskeyFromWallet.test.d.ts.map +1 -0
- package/dist/test/unit/removePasskeyFromWallet.test.js +170 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +7 -5
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
const assert = __importStar(require("assert"));
|
|
37
|
+
const sinon = __importStar(require("sinon"));
|
|
38
|
+
const attachPasskeyToWallet_1 = require("../../src/attachPasskeyToWallet");
|
|
39
|
+
describe('attachPasskeyToWallet', function () {
|
|
40
|
+
const coin = 'tbtc';
|
|
41
|
+
const walletId = 'wallet-abc123';
|
|
42
|
+
const keychainId = 'key-user-id';
|
|
43
|
+
const enterpriseId = 'enterprise-xyz';
|
|
44
|
+
const encryptedPrv = 'encrypted-prv-string';
|
|
45
|
+
const decryptedPrv = 'xprv-decrypted';
|
|
46
|
+
const existingPassphrase = 'correct-passphrase';
|
|
47
|
+
const reEncryptedPrv = 're-encrypted-prv';
|
|
48
|
+
const prfResultBuffer = new Uint8Array([0x1e, 0x5c, 0xb4, 0x78]).buffer;
|
|
49
|
+
const device = {
|
|
50
|
+
id: 'mongo-object-id-123',
|
|
51
|
+
credentialId: 'cred-id-456',
|
|
52
|
+
prfSalt: 'ZqJ64M2dL65zn2-Jxd58SMN2ILc9QjbCFxUTGHd_LC8',
|
|
53
|
+
isPasskey: true,
|
|
54
|
+
};
|
|
55
|
+
const mockAuthResult = {
|
|
56
|
+
prfResult: prfResultBuffer,
|
|
57
|
+
credentialId: 'cred-id-456',
|
|
58
|
+
otpCode: '123456',
|
|
59
|
+
};
|
|
60
|
+
const updatedKeychain = {
|
|
61
|
+
id: keychainId,
|
|
62
|
+
pub: 'xpub-123',
|
|
63
|
+
type: 'independent',
|
|
64
|
+
encryptedPrv,
|
|
65
|
+
};
|
|
66
|
+
let mockWallet;
|
|
67
|
+
let mockWallets;
|
|
68
|
+
let mockBaseCoin;
|
|
69
|
+
let mockBitGo;
|
|
70
|
+
let mockProvider;
|
|
71
|
+
beforeEach(function () {
|
|
72
|
+
mockWallet = {
|
|
73
|
+
type: sinon.stub().returns('hot'),
|
|
74
|
+
toJSON: sinon.stub().returns({ enterprise: enterpriseId }),
|
|
75
|
+
getEncryptedUserKeychain: sinon.stub().resolves({ id: keychainId, encryptedPrv }),
|
|
76
|
+
};
|
|
77
|
+
mockWallets = {
|
|
78
|
+
get: sinon.stub().resolves(mockWallet),
|
|
79
|
+
};
|
|
80
|
+
mockBaseCoin = {
|
|
81
|
+
wallets: sinon.stub().returns(mockWallets),
|
|
82
|
+
};
|
|
83
|
+
mockBitGo = {
|
|
84
|
+
url: sinon
|
|
85
|
+
.stub()
|
|
86
|
+
.callsFake((path, version) => `/api/v${version ?? 1}${path}`),
|
|
87
|
+
coin: sinon.stub().returns(mockBaseCoin),
|
|
88
|
+
put: sinon.stub(),
|
|
89
|
+
decrypt: sinon.stub(),
|
|
90
|
+
encrypt: sinon.stub(),
|
|
91
|
+
};
|
|
92
|
+
mockProvider = {
|
|
93
|
+
create: sinon.stub(),
|
|
94
|
+
get: sinon.stub(),
|
|
95
|
+
};
|
|
96
|
+
mockBitGo.decrypt.returns(decryptedPrv);
|
|
97
|
+
mockBitGo.encrypt.returns(reEncryptedPrv);
|
|
98
|
+
const putSendStub = sinon.stub().returns({ result: sinon.stub().resolves(updatedKeychain) });
|
|
99
|
+
mockBitGo.put.returns({ send: putSendStub });
|
|
100
|
+
mockProvider.get.resolves(mockAuthResult);
|
|
101
|
+
});
|
|
102
|
+
afterEach(function () {
|
|
103
|
+
sinon.restore();
|
|
104
|
+
});
|
|
105
|
+
async function callAttach(overrides) {
|
|
106
|
+
return (0, attachPasskeyToWallet_1.attachPasskeyToWallet)({
|
|
107
|
+
bitgo: mockBitGo,
|
|
108
|
+
coin,
|
|
109
|
+
walletId,
|
|
110
|
+
device,
|
|
111
|
+
existingPassphrase,
|
|
112
|
+
provider: mockProvider,
|
|
113
|
+
...overrides,
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
it('should attach a passkey and return the updated keychain', async function () {
|
|
117
|
+
const result = await callAttach();
|
|
118
|
+
sinon.assert.calledWith(mockBitGo.coin, coin);
|
|
119
|
+
sinon.assert.calledWith(mockWallets.get, { id: walletId });
|
|
120
|
+
sinon.assert.calledOnce(mockWallet.type);
|
|
121
|
+
sinon.assert.calledOnce(mockWallet.getEncryptedUserKeychain);
|
|
122
|
+
sinon.assert.calledOnce(mockBitGo.decrypt);
|
|
123
|
+
sinon.assert.calledWithExactly(mockBitGo.decrypt, { password: existingPassphrase, input: encryptedPrv });
|
|
124
|
+
// provider.get called with evalByCredential keyed on device.credentialId
|
|
125
|
+
sinon.assert.calledOnce(mockProvider.get);
|
|
126
|
+
const getArgs = mockProvider.get.firstCall.args[0];
|
|
127
|
+
assert.ok(getArgs.evalByCredential);
|
|
128
|
+
assert.strictEqual(typeof getArgs.evalByCredential[device.credentialId], 'string');
|
|
129
|
+
// allowCredentials must be populated with the credential ID as an ArrayBuffer
|
|
130
|
+
assert.ok(Array.isArray(getArgs.publicKey.allowCredentials));
|
|
131
|
+
assert.strictEqual(getArgs.publicKey.allowCredentials.length, 1);
|
|
132
|
+
assert.strictEqual(getArgs.publicKey.allowCredentials[0].type, 'public-key');
|
|
133
|
+
assert.ok(getArgs.publicKey.allowCredentials[0].id instanceof ArrayBuffer);
|
|
134
|
+
// PUT called with correct shape
|
|
135
|
+
sinon.assert.calledOnce(mockBitGo.put);
|
|
136
|
+
sinon.assert.calledWith(mockBitGo.put, `/api/v2/${coin}/key/${keychainId}`);
|
|
137
|
+
const sendStub = mockBitGo.put.firstCall.returnValue.send;
|
|
138
|
+
sinon.assert.calledOnce(sendStub);
|
|
139
|
+
const putBody = sendStub.firstCall.args[0];
|
|
140
|
+
assert.ok(putBody.webauthnInfo);
|
|
141
|
+
assert.strictEqual(putBody.webauthnInfo.otpDeviceId, device.id);
|
|
142
|
+
// prfSalt must be base64url (URL-safe, no padding) as required by server validation
|
|
143
|
+
assert.match(putBody.webauthnInfo.prfSalt, /^[A-Za-z0-9\-_]+$/);
|
|
144
|
+
assert.strictEqual(typeof putBody.webauthnInfo.encryptedPrv, 'string');
|
|
145
|
+
assert.strictEqual(result.id, keychainId);
|
|
146
|
+
});
|
|
147
|
+
it('should decode credentialId containing base64url-specific characters (- and _)', async function () {
|
|
148
|
+
const deviceWithUrlChars = {
|
|
149
|
+
...device,
|
|
150
|
+
credentialId: 'abc-def_ghi+jkl',
|
|
151
|
+
};
|
|
152
|
+
const result = await callAttach({ device: deviceWithUrlChars });
|
|
153
|
+
assert.ok(result);
|
|
154
|
+
const getArgs = mockProvider.get.firstCall.args[0];
|
|
155
|
+
assert.ok(getArgs.publicKey.allowCredentials[0].id instanceof ArrayBuffer);
|
|
156
|
+
});
|
|
157
|
+
it('should throw if device.prfSalt is undefined', async function () {
|
|
158
|
+
const deviceNoPrf = { ...device, prfSalt: undefined };
|
|
159
|
+
await assert.rejects(() => callAttach({ device: deviceNoPrf }), (err) => {
|
|
160
|
+
assert.strictEqual(err.message, 'PRF extension not supported by this device. Please use a different passkey.');
|
|
161
|
+
return true;
|
|
162
|
+
});
|
|
163
|
+
sinon.assert.notCalled(mockBitGo.coin);
|
|
164
|
+
sinon.assert.notCalled(mockBitGo.put);
|
|
165
|
+
});
|
|
166
|
+
it('should throw if wallet is not a hot wallet', async function () {
|
|
167
|
+
mockWallet.type.returns('cold');
|
|
168
|
+
await assert.rejects(() => callAttach(), (err) => {
|
|
169
|
+
assert.ok(err.message.includes('not a hot wallet'));
|
|
170
|
+
return true;
|
|
171
|
+
});
|
|
172
|
+
sinon.assert.notCalled(mockBitGo.put);
|
|
173
|
+
});
|
|
174
|
+
it('should throw if wallet has no enterprise', async function () {
|
|
175
|
+
mockWallet.toJSON.returns({ enterprise: undefined });
|
|
176
|
+
await assert.rejects(() => callAttach(), (err) => {
|
|
177
|
+
assert.ok(err.message.includes('has no enterprise'));
|
|
178
|
+
return true;
|
|
179
|
+
});
|
|
180
|
+
});
|
|
181
|
+
it('should throw if PRF assertion returns no result', async function () {
|
|
182
|
+
mockProvider.get.resolves({ ...mockAuthResult, prfResult: undefined });
|
|
183
|
+
await assert.rejects(() => callAttach(), (err) => {
|
|
184
|
+
assert.ok(err.message.includes('PRF assertion did not return a result'));
|
|
185
|
+
return true;
|
|
186
|
+
});
|
|
187
|
+
sinon.assert.notCalled(mockBitGo.put);
|
|
188
|
+
});
|
|
189
|
+
it('should propagate decrypt errors', async function () {
|
|
190
|
+
mockBitGo.decrypt.throws(new Error('decryption failed'));
|
|
191
|
+
await assert.rejects(() => callAttach(), (err) => {
|
|
192
|
+
assert.ok(err.message.includes('decryption failed'));
|
|
193
|
+
return true;
|
|
194
|
+
});
|
|
195
|
+
sinon.assert.notCalled(mockBitGo.put);
|
|
196
|
+
});
|
|
197
|
+
it('should use device.credentialId as the key in evalByCredential', async function () {
|
|
198
|
+
await callAttach();
|
|
199
|
+
const getArgs = mockProvider.get.firstCall.args[0];
|
|
200
|
+
const evalKeys = Object.keys(getArgs.evalByCredential);
|
|
201
|
+
assert.strictEqual(evalKeys.length, 1);
|
|
202
|
+
assert.strictEqual(evalKeys[0], device.credentialId);
|
|
203
|
+
});
|
|
204
|
+
});
|
|
205
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXR0YWNoUGFzc2tleVRvV2FsbGV0LnRlc3QuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi90ZXN0L3VuaXQvYXR0YWNoUGFzc2tleVRvV2FsbGV0LnRlc3QudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSwrQ0FBaUM7QUFDakMsNkNBQStCO0FBQy9CLDJFQUF3RTtBQUd4RSxRQUFRLENBQUMsdUJBQXVCLEVBQUU7SUFDaEMsTUFBTSxJQUFJLEdBQUcsTUFBTSxDQUFDO0lBQ3BCLE1BQU0sUUFBUSxHQUFHLGVBQWUsQ0FBQztJQUNqQyxNQUFNLFVBQVUsR0FBRyxhQUFhLENBQUM7SUFDakMsTUFBTSxZQUFZLEdBQUcsZ0JBQWdCLENBQUM7SUFDdEMsTUFBTSxZQUFZLEdBQUcsc0JBQXNCLENBQUM7SUFDNUMsTUFBTSxZQUFZLEdBQUcsZ0JBQWdCLENBQUM7SUFDdEMsTUFBTSxrQkFBa0IsR0FBRyxvQkFBb0IsQ0FBQztJQUNoRCxNQUFNLGNBQWMsR0FBRyxrQkFBa0IsQ0FBQztJQUUxQyxNQUFNLGVBQWUsR0FBRyxJQUFJLFVBQVUsQ0FBQyxDQUFDLElBQUksRUFBRSxJQUFJLEVBQUUsSUFBSSxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsTUFBTSxDQUFDO0lBRXhFLE1BQU0sTUFBTSxHQUFzQjtRQUNoQyxFQUFFLEVBQUUscUJBQXFCO1FBQ3pCLFlBQVksRUFBRSxhQUFhO1FBQzNCLE9BQU8sRUFBRSw2Q0FBNkM7UUFDdEQsU0FBUyxFQUFFLElBQUk7S0FDaEIsQ0FBQztJQUVGLE1BQU0sY0FBYyxHQUFzQjtRQUN4QyxTQUFTLEVBQUUsZUFBZTtRQUMxQixZQUFZLEVBQUUsYUFBYTtRQUMzQixPQUFPLEVBQUUsUUFBUTtLQUNsQixDQUFDO0lBRUYsTUFBTSxlQUFlLEdBQUc7UUFDdEIsRUFBRSxFQUFFLFVBQVU7UUFDZCxHQUFHLEVBQUUsVUFBVTtRQUNmLElB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b3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBhc3NlcnQgZnJvbSAnYXNzZXJ0JztcbmltcG9ydCAqIGFzIHNpbm9uIGZyb20gJ3Npbm9uJztcbmltcG9ydCB7IGF0dGFjaFBhc3NrZXlUb1dhbGxldCB9IGZyb20gJy4uLy4uL3NyYy9hdHRhY2hQYXNza2V5VG9XYWxsZXQnO1xuaW1wb3J0IHsgV2ViQXV0aG5PdHBEZXZpY2UsIFBhc3NrZXlBdXRoUmVzdWx0LCBXZWJBdXRoblByb3ZpZGVyIH0gZnJvbSAnLi4vLi4vc3JjL3dlYkF1dGhuVHlwZXMnO1xuXG5kZXNjcmliZSgnYXR0YWNoUGFzc2tleVRvV2FsbGV0JywgZnVuY3Rpb24gKCkge1xuICBjb25zdCBjb2luID0gJ3RidGMnO1xuICBjb25zdCB3YWxsZXRJZCA9ICd3YWxsZXQtYWJjMTIzJztcbiAgY29uc3Qga2V5Y2hhaW5JZCA9ICdrZXktdXNlci1pZCc7XG4gIGNvbnN0IGVudGVycHJpc2VJZCA9ICdlbnRlcnByaXNlLXh5eic7XG4gIGNvbnN0IGVuY3J5cHRlZFBydiA9ICdlbmNyeXB0ZWQtcHJ2LXN0cmluZyc7XG4gIGNvbnN0IGRlY3J5cHRlZFBydiA9ICd4cHJ2LWRlY3J5cHRlZCc7XG4gIGNvbnN0IGV4aXN0aW5nUGFzc3BocmFzZSA9ICdjb3JyZWN0LXBhc3NwaHJhc2UnO1xuICBjb25zdCByZUVuY3J5cHRlZFBydiA9ICdyZS1lbmNyeXB0ZWQtcHJ2JztcblxuICBjb25zdCBwcmZSZXN1bHRCdWZmZXIgPSBuZXcgVWludDhBcnJheShbMHgxZSwgMHg1YywgMHhiNCwgMHg3OF0pLmJ1ZmZlcjtcblxuICBjb25zdCBkZXZpY2U6IFdlYkF1dGhuT3RwRGV2aWNlID0ge1xuICAgIGlkOiAnbW9uZ28tb2JqZWN0LWlkLTEyMycsXG4gICAgY3JlZGVudGlhbElkOiAnY3JlZC1pZC00NTYnLFxuICAgIHByZlNhbHQ6ICdacUo2NE0yZEw2NXpuMi1KeGQ1OFNNTjJJTGM5UWpiQ0Z4VVRHSGRfTEM4JyxcbiAgICBpc1Bhc3NrZXk6IHRydWUsXG4gIH07XG5cbiAgY29uc3QgbW9ja0F1dGhSZXN1bHQ6IFBhc3NrZXlBdXRoUmVzdWx0ID0ge1xuICAgIHByZlJlc3VsdDogcHJmUmVzdWx0QnVmZmVyLFxuICAgIGNyZWRlbnRpYWxJZDogJ2NyZWQtaWQtNDU2JyxcbiAgICBvdHBDb2RlOiAnMTIzNDU2JyxcbiAgfTtcblxuICBjb25zdCB1cGRhdGVkS2V5Y2hhaW4gPSB7XG4gICAgaWQ6IGtleWNoYWluSWQsXG4gICAgcHViOiAneHB1Yi0xMjMnLFxuICAgIHR5cGU6ICdpbmRlcGVuZGVudCcgYXMgY29uc3QsXG4gICAgZW5jcnlwdGVkUHJ2LFxuICB9O1xuXG4gIGxldCBtb2NrV2FsbGV0OiB7XG4gICAgdHlwZTogc2lub24uU2lub25TdHViO1xuICAgIHRvSlNPTjogc2lub24uU2lub25TdHViO1xuICAgIGdldEVuY3J5cHRlZFVzZXJLZXljaGFpbjogc2lub24uU2lub25TdHViO1xuICB9O1xuXG4gIGxldCBtb2NrV2FsbGV0czoge1xuICAgIGdldDogc2lub24uU2lub25TdHViO1xuICB9O1xuXG4gIGxldCBtb2NrQmFzZUNvaW46IHtcbiAgICB3YWxsZXRzOiBzaW5vbi5TaW5vblN0dWI7XG4gIH07XG5cbiAgbGV0IG1vY2tCaXRHbzoge1xuICAgIHVybDogc2lub24uU2lub25TdHViO1xuICAgIGNvaW46IHNpbm9uLlNpbm9uU3R1YjtcbiAgICBwdXQ6IHNpbm9uLlNpbm9uU3R1YjtcbiAgICBkZWNyeXB0OiBzaW5vbi5TaW5vblN0dWI7XG4gICAgZW5jcnlwdDogc2lub24uU2lub25TdHViO1xuICB9O1xuXG4gIGxldCBtb2NrUHJvdmlkZXI6IHtcbiAgICBjcmVhdGU6IHNpbm9uLlNpbm9uU3R1YjtcbiAgICBnZXQ6IHNpbm9uLlNpbm9uU3R1YjtcbiAgfTtcblxuICBiZWZvcmVFYWNoKGZ1bmN0aW9uICgpIHtcbiAgICBtb2NrV2FsbGV0ID0ge1xuICAgICAgdHlwZTogc2lub24uc3R1YigpLnJldHVybnMoJ2hvdCcpLFxuICAgICAgdG9KU09OOiBzaW5vbi5zdHViKCkucmV0dXJucyh7IGVudGVycHJpc2U6IGVudGVycHJpc2VJZCB9KSxcbiAgICAgIGdldEVuY3J5cHRlZFVzZXJLZXljaGFpbjogc2lub24uc3R1YigpLnJlc29sdmVzKHsgaWQ6IGtleWNoYWluSWQsIGVuY3J5cHRlZFBydiB9KSxcbiAgICB9O1xuXG4gICAgbW9ja1dhbGxldHMgPSB7XG4gICAgICBnZXQ6IHNpbm9uLnN0dWIoKS5yZXNvbHZlcyhtb2NrV2FsbGV0KSxcbiAgICB9O1xuXG4gICAgbW9ja0Jhc2VDb2luID0ge1xuICAgICAgd2FsbGV0czogc2lub24uc3R1YigpLnJldHVybnMobW9ja1dhbGxldHMpLFxuICAgIH07XG5cbiAgICBtb2NrQml0R28gPSB7XG4gICAgICB1cmw6IHNpbm9uXG4gICAgICAgIC5zdHViPFtwYXRoOiBzdHJpbmcsIHZlcnNpb24/OiBudW1iZXJdLCBzdHJpbmc+KClcbiAgICAgICAgLmNhbGxzRmFrZSgocGF0aCwgdmVyc2lvbikgPT4gYC9hcGkvdiR7dmVyc2lvbiA/PyAxfSR7cGF0aH1gKSxcbiAgICAgIGNvaW46IHNpbm9uLnN0dWIoKS5yZXR1cm5zKG1vY2tCYXNlQ29pbiksXG4gICAgICBwdXQ6IHNpbm9uLnN0dWIoKSxcbiAgICAgIGRlY3J5cHQ6IHNpbm9uLnN0dWIoKSxcbiAgICAgIGVuY3J5cHQ6IHNpbm9uLnN0dWIoKSxcbiAgICB9O1xuXG4gICAgbW9ja1Byb3ZpZGVyID0ge1xuICAgICAgY3JlYXRlOiBzaW5vbi5zdHViKCksXG4gICAgICBnZXQ6IHNpbm9uLnN0dWIoKSxcbiAgICB9O1xuXG4gICAgbW9ja0JpdEdvLmRlY3J5cHQucmV0dXJucyhkZWNyeXB0ZWRQcnYpO1xuICAgIG1vY2tCaXRHby5lbmNyeXB0LnJldHVybnMocmVFbmNyeXB0ZWRQcnYpO1xuXG4gICAgY29uc3QgcHV0U2VuZFN0dWIgPSBzaW5vbi5zdHViKCkucmV0dXJucyh7IHJlc3VsdDogc2lub24uc3R1YigpLnJlc29sdmVzKHVwZGF0ZWRLZXljaGFpbikgfSk7XG4gICAgbW9ja0JpdEdvLnB1dC5yZXR1cm5zKHsgc2VuZDogcHV0U2VuZFN0dWIgfSk7XG5cbiAgICBtb2NrUHJvdmlkZXIuZ2V0LnJlc29sdmVzKG1vY2tBdXRoUmVzdWx0KTtcbiAgfSk7XG5cbiAgYWZ0ZXJFYWNoKGZ1bmN0aW9uICgpIHtcbiAgICBzaW5vbi5yZXN0b3JlKCk7XG4gIH0pO1xuXG4gIGFzeW5jIGZ1bmN0aW9uIGNhbGxBdHRhY2gob3ZlcnJpZGVzPzogUGFydGlhbDxQYXJhbWV0ZXJzPHR5cGVvZiBhdHRhY2hQYXNza2V5VG9XYWxsZXQ+WzBdPikge1xuICAgIHJldHVybiBhdHRhY2hQYXNza2V5VG9XYWxsZXQoe1xuICAgICAgYml0Z286IG1vY2tCaXRHbyBhcyB1bmtub3duIGFzIFBhcmFtZXRlcnM8dHlwZW9mIGF0dGFjaFBhc3NrZXlUb1dhbGxldD5bMF1bJ2JpdGdvJ10sXG4gICAgICBjb2luLFxuICAgICAgd2FsbGV0SWQsXG4gICAgICBkZXZpY2UsXG4gICAgICBleGlzdGluZ1Bhc3NwaHJhc2UsXG4gICAgICBwcm92aWRlcjogbW9ja1Byb3ZpZGVyIGFzIHVua25vd24gYXMgV2ViQXV0aG5Qcm92aWRlcixcbiAgICAgIC4uLm92ZXJyaWRlcyxcbiAgICB9KTtcbiAgfVxuXG4gIGl0KCdzaG91bGQgYXR0YWNoIGEgcGFzc2tleSBhbmQgcmV0dXJuIHRoZSB1cGRhdGVkIGtleWNoYWluJywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGNhbGxBdHRhY2goKTtcblxuICAgIHNpbm9uLmFzc2VydC5jYWxsZWRXaXRoKG1vY2tCaXRHby5jb2luLCBjb2luKTtcbiAgICBzaW5vbi5hc3NlcnQuY2FsbGVkV2l0aChtb2NrV2FsbGV0cy5nZXQsIHsgaWQ6IHdhbGxldElkIH0pO1xuICAgIHNpbm9uLmFzc2VydC5jYWxsZWRPbmNlKG1vY2tXYWxsZXQudHlwZSk7XG4gICAgc2lub24uYXNzZXJ0LmNhbGxlZE9uY2UobW9ja1dhbGxldC5nZXRFbmNyeXB0ZWRVc2VyS2V5Y2hhaW4pO1xuICAgIHNpbm9uLmFzc2VydC5jYWxsZWRPbmNlKG1vY2tCaXRHby5kZWNyeXB0KTtcbiAgICBzaW5vbi5hc3NlcnQuY2FsbGVkV2l0aEV4YWN0bHkobW9ja0JpdEdvLmRlY3J5cHQsIHsgcGFzc3dvcmQ6IGV4aXN0aW5nUGFzc3BocmFzZSwgaW5wdXQ6IGVuY3J5cHRlZFBydiB9KTtcblxuICAgIC8vIHByb3ZpZGVyLmdldCBjYWxsZWQgd2l0aCBldmFsQnlDcmVkZW50aWFsIGtleWVkIG9uIGRldmljZS5jcmVkZW50aWFsSWRcbiAgICBzaW5vbi5hc3NlcnQuY2FsbGVkT25jZShtb2NrUHJvdmlkZXIuZ2V0KTtcbiAgICBjb25zdCBnZXRBcmdzID0gbW9ja1Byb3ZpZGVyLmdldC5maXJzdENhbGwuYXJnc1swXTtcbiAgICBhc3NlcnQub2soZ2V0QXJncy5ldmFsQnlDcmVkZW50aWFsKTtcbiAgICBhc3NlcnQuc3RyaWN0RXF1YWwodHlwZW9mIGdldEFyZ3MuZXZhbEJ5Q3JlZGVudGlhbFtkZXZpY2UuY3JlZGVudGlhbElkXSwgJ3N0cmluZycpO1xuXG4gICAgLy8gYWxsb3dDcmVkZW50aWFscyBtdXN0IGJlIHBvcHVsYXRlZCB3aXRoIHRoZSBjcmVkZW50aWFsIElEIGFzIGFuIEFycmF5QnVmZmVyXG4gICAgYXNzZXJ0Lm9rKEFycmF5LmlzQXJyYXkoZ2V0QXJncy5wdWJsaWNLZXkuYWxsb3dDcmVkZW50aWFscykpO1xuICAgIGFzc2VydC5zdHJpY3RFcXVhbChnZXRBcmdzLnB1YmxpY0tleS5hbGxvd0NyZWRlbnRpYWxzLmxlbmd0aCwgMSk7XG4gICAgYXNzZXJ0LnN0cmljdEVxdWFsKGdldEFyZ3MucHVibGljS2V5LmFsbG93Q3JlZGVudGlhbHNbMF0udHlwZSwgJ3B1YmxpYy1rZXknKTtcbiAgICBhc3NlcnQub2soZ2V0QXJncy5wdWJsaWNLZXkuYWxsb3dDcmVkZW50aWFsc1swXS5pZCBpbnN0YW5jZW9mIEFycmF5QnVmZmVyKTtcblxuICAgIC8vIFBVVCBjYWxsZWQgd2l0aCBjb3JyZWN0IHNoYXBlXG4gICAgc2lub24uYXNzZXJ0LmNhbGxlZE9uY2UobW9ja0JpdEdvLnB1dCk7XG4gICAgc2lub24uYXNzZXJ0LmNhbGxlZFdpdGgobW9ja0JpdEdvLnB1dCwgYC9hcGkvdjIvJHtjb2lufS9rZXkvJHtrZXljaGFpbklkfWApO1xuICAgIGNvbnN0IHNlbmRTdHViID0gbW9ja0JpdEdvLnB1dC5maXJzdENhbGwucmV0dXJuVmFsdWUuc2VuZDtcbiAgICBzaW5vbi5hc3NlcnQuY2FsbGVkT25jZShzZW5kU3R1Yik7XG4gICAgY29uc3QgcHV0Qm9keSA9IHNlbmRTdHViLmZpcnN0Q2FsbC5hcmdzWzBdO1xuICAgIGFzc2VydC5vayhwdXRCb2R5LndlYmF1dGhuSW5mbyk7XG4gICAgYXNzZXJ0LnN0cmljdEVxdWFsKHB1dEJvZHkud2ViYXV0aG5JbmZvLm90cERldmljZUlkLCBkZXZpY2UuaWQpO1xuICAgIC8vIHByZlNhbHQgbXVzdCBiZSBiYXNlNjR1cmwgKFVSTC1zYWZlLCBubyBwYWRkaW5nKSBhcyByZXF1aXJlZCBieSBzZXJ2ZXIgdmFsaWRhdGlvblxuICAgIGFzc2VydC5tYXRjaChwdXRCb2R5LndlYmF1dGhuSW5mby5wcmZTYWx0LCAvXltBLVphLXowLTlcXC1fXSskLyk7XG4gICAgYXNzZXJ0LnN0cmljdEVxdWFsKHR5cGVvZiBwdXRCb2R5LndlYmF1dGhuSW5mby5lbmNyeXB0ZWRQcnYsICdzdHJpbmcnKTtcblxuICAgIGFzc2VydC5zdHJpY3RFcXVhbChyZXN1bHQuaWQsIGtleWNoYWluSWQpO1xuICB9KTtcblxuICBpdCgnc2hvdWxkIGRlY29kZSBjcmVkZW50aWFsSWQgY29udGFpbmluZyBiYXNlNjR1cmwtc3BlY2lmaWMgY2hhcmFjdGVycyAoLSBhbmQgXyknLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgY29uc3QgZGV2aWNlV2l0aFVybENoYXJzOiBXZWJBdXRobk90cERldmljZSA9IHtcbiAgICAgIC4uLmRldmljZSxcbiAgICAgIGNyZWRlbnRpYWxJZDogJ2FiYy1kZWZfZ2hpK2prbCcsXG4gICAgfTtcblxuICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGNhbGxBdHRhY2goeyBkZXZpY2U6IGRldmljZVdpdGhVcmxDaGFycyB9KTtcbiAgICBhc3NlcnQub2socmVzdWx0KTtcblxuICAgIGNvbnN0IGdldEFyZ3MgPSBtb2NrUHJvdmlkZXIuZ2V0LmZpcnN0Q2FsbC5hcmdzWzBdO1xuICAgIGFzc2VydC5vayhnZXRBcmdzLnB1YmxpY0tleS5hbGxvd0NyZWRlbnRpYWxzWzBdLmlkIGluc3RhbmNlb2YgQXJyYXlCdWZmZXIpO1xuICB9KTtcblxuICBpdCgnc2hvdWxkIHRocm93IGlmIGRldmljZS5wcmZTYWx0IGlzIHVuZGVmaW5lZCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCBkZXZpY2VOb1ByZjogV2ViQXV0aG5PdHBEZXZpY2UgPSB7IC4uLmRldmljZSwgcHJmU2FsdDogdW5kZWZpbmVkIH07XG5cbiAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICgpID0+IGNhbGxBdHRhY2goeyBkZXZpY2U6IGRldmljZU5vUHJmIH0pLFxuICAgICAgKGVycjogRXJyb3IpID0+IHtcbiAgICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKGVyci5tZXNzYWdlLCAnUFJGIGV4dGVuc2lvbiBub3Qgc3VwcG9ydGVkIGJ5IHRoaXMgZGV2aWNlLiBQbGVhc2UgdXNlIGEgZGlmZmVyZW50IHBhc3NrZXkuJyk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgICk7XG5cbiAgICBzaW5vbi5hc3NlcnQubm90Q2FsbGVkKG1vY2tCaXRHby5jb2luKTtcbiAgICBzaW5vbi5hc3NlcnQubm90Q2FsbGVkKG1vY2tCaXRHby5wdXQpO1xuICB9KTtcblxuICBpdCgnc2hvdWxkIHRocm93IGlmIHdhbGxldCBpcyBub3QgYSBob3Qgd2FsbGV0JywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIG1vY2tXYWxsZXQudHlwZS5yZXR1cm5zKCdjb2xkJyk7XG5cbiAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICgpID0+IGNhbGxBdHRhY2goKSxcbiAgICAgIChlcnI6IEVycm9yKSA9PiB7XG4gICAgICAgIGFzc2VydC5vayhlcnIubWVzc2FnZS5pbmNsdWRlcygnbm90IGEgaG90IHdhbGxldCcpKTtcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICB9XG4gICAgKTtcblxuICAgIHNpbm9uLmFzc2VydC5ub3RDYWxsZWQobW9ja0JpdEdvLnB1dCk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgdGhyb3cgaWYgd2FsbGV0IGhhcyBubyBlbnRlcnByaXNlJywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIG1vY2tXYWxsZXQudG9KU09OLnJldHVybnMoeyBlbnRlcnByaXNlOiB1bmRlZmluZWQgfSk7XG5cbiAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICgpID0+IGNhbGxBdHRhY2goKSxcbiAgICAgIChlcnI6IEVycm9yKSA9PiB7XG4gICAgICAgIGFzc2VydC5vayhlcnIubWVzc2FnZS5pbmNsdWRlcygnaGFzIG5vIGVudGVycHJpc2UnKSk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgICk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgdGhyb3cgaWYgUFJGIGFzc2VydGlvbiByZXR1cm5zIG5vIHJlc3VsdCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICBtb2NrUHJvdmlkZXIuZ2V0LnJlc29sdmVzKHsgLi4ubW9ja0F1dGhSZXN1bHQsIHByZlJlc3VsdDogdW5kZWZpbmVkIH0pO1xuXG4gICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoXG4gICAgICAoKSA9PiBjYWxsQXR0YWNoKCksXG4gICAgICAoZXJyOiBFcnJvcikgPT4ge1xuICAgICAgICBhc3NlcnQub2soZXJyLm1lc3NhZ2UuaW5jbHVkZXMoJ1BSRiBhc3NlcnRpb24gZGlkIG5vdCByZXR1cm4gYSByZXN1bHQnKSk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgICk7XG5cbiAgICBzaW5vbi5hc3NlcnQubm90Q2FsbGVkKG1vY2tCaXRHby5wdXQpO1xuICB9KTtcblxuICBpdCgnc2hvdWxkIHByb3BhZ2F0ZSBkZWNyeXB0IGVycm9ycycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICBtb2NrQml0R28uZGVjcnlwdC50aHJvd3MobmV3IEVycm9yKCdkZWNyeXB0aW9uIGZhaWxlZCcpKTtcblxuICAgIGF3YWl0IGFzc2VydC5yZWplY3RzKFxuICAgICAgKCkgPT4gY2FsbEF0dGFjaCgpLFxuICAgICAgKGVycjogRXJyb3IpID0+IHtcbiAgICAgICAgYXNzZXJ0Lm9rKGVyci5tZXNzYWdlLmluY2x1ZGVzKCdkZWNyeXB0aW9uIGZhaWxlZCcpKTtcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICB9XG4gICAgKTtcblxuICAgIHNpbm9uLmFzc2VydC5ub3RDYWxsZWQobW9ja0JpdEdvLnB1dCk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgdXNlIGRldmljZS5jcmVkZW50aWFsSWQgYXMgdGhlIGtleSBpbiBldmFsQnlDcmVkZW50aWFsJywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIGF3YWl0IGNhbGxBdHRhY2goKTtcblxuICAgIGNvbnN0IGdldEFyZ3MgPSBtb2NrUHJvdmlkZXIuZ2V0LmZpcnN0Q2FsbC5hcmdzWzBdO1xuICAgIGNvbnN0IGV2YWxLZXlzID0gT2JqZWN0LmtleXMoZ2V0QXJncy5ldmFsQnlDcmVkZW50aWFsKTtcbiAgICBhc3NlcnQuc3RyaWN0RXF1YWwoZXZhbEtleXMubGVuZ3RoLCAxKTtcbiAgICBhc3NlcnQuc3RyaWN0RXF1YWwoZXZhbEtleXNbMF0sIGRldmljZS5jcmVkZW50aWFsSWQpO1xuICB9KTtcbn0pO1xuIl19
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"base64url.test.d.ts","sourceRoot":"","sources":["../../../test/unit/base64url.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
const assert = __importStar(require("assert"));
|
|
37
|
+
const base64url_1 = require("../../src/base64url");
|
|
38
|
+
describe('base64url helpers', function () {
|
|
39
|
+
describe('toBase64Url', function () {
|
|
40
|
+
it('replaces +, / and strips padding', function () {
|
|
41
|
+
assert.strictEqual((0, base64url_1.toBase64Url)('a+b/c=='), 'a-b_c');
|
|
42
|
+
});
|
|
43
|
+
it('is a no-op on already-base64url input', function () {
|
|
44
|
+
assert.strictEqual((0, base64url_1.toBase64Url)('a-b_c'), 'a-b_c');
|
|
45
|
+
});
|
|
46
|
+
it('handles empty string', function () {
|
|
47
|
+
assert.strictEqual((0, base64url_1.toBase64Url)(''), '');
|
|
48
|
+
});
|
|
49
|
+
});
|
|
50
|
+
describe('bufferToBase64Url', function () {
|
|
51
|
+
it('encodes a Buffer to unpadded base64url', function () {
|
|
52
|
+
// bytes that produce + and / in standard base64
|
|
53
|
+
const buf = Buffer.from([0xfb, 0xff, 0xbf]);
|
|
54
|
+
assert.strictEqual(buf.toString('base64'), '+/+/');
|
|
55
|
+
assert.strictEqual((0, base64url_1.bufferToBase64Url)(buf), '-_-_');
|
|
56
|
+
});
|
|
57
|
+
it('encodes an ArrayBuffer to unpadded base64url', function () {
|
|
58
|
+
const ab = new Uint8Array([0xff, 0xfe, 0xfd]).buffer;
|
|
59
|
+
assert.strictEqual((0, base64url_1.bufferToBase64Url)(ab), '__79');
|
|
60
|
+
});
|
|
61
|
+
});
|
|
62
|
+
describe('base64UrlToBuffer', function () {
|
|
63
|
+
it('round-trips through bufferToBase64Url', function () {
|
|
64
|
+
const original = Buffer.from([0x00, 0xff, 0x10, 0x20, 0xab, 0xcd]);
|
|
65
|
+
const encoded = (0, base64url_1.bufferToBase64Url)(original);
|
|
66
|
+
const decoded = (0, base64url_1.base64UrlToBuffer)(encoded);
|
|
67
|
+
assert.deepStrictEqual(decoded, original);
|
|
68
|
+
});
|
|
69
|
+
it('decodes base64url with - and _ chars', function () {
|
|
70
|
+
const decoded = (0, base64url_1.base64UrlToBuffer)('-_-_');
|
|
71
|
+
assert.deepStrictEqual(decoded, Buffer.from([0xfb, 0xff, 0xbf]));
|
|
72
|
+
});
|
|
73
|
+
});
|
|
74
|
+
});
|
|
75
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYmFzZTY0dXJsLnRlc3QuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi90ZXN0L3VuaXQvYmFzZTY0dXJsLnRlc3QudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSwrQ0FBaUM7QUFDakMsbURBQXdGO0FBRXhGLFFBQVEsQ0FBQyxtQkFBbUIsRUFBRTtJQUM1QixRQUFRLENBQUMsYUFBYSxFQUFFO1FBQ3RCLEVBQUUsQ0FBQyxrQ0FBa0MsRUFBRTtZQUNyQyxNQUFNLENBQUMsV0FBVyxDQUFDLElBQUEsdUJBQVcsRUFBQyxTQUFTLENBQUMsRUFBRSxPQUFPLENBQUMsQ0FBQztRQUN0RCxDQUFDLENBQUMsQ0FBQztRQUVILEVBQUUsQ0FBQyx1Q0FBdUMsRUFBRTtZQUMxQyxNQUFNLENBQUMsV0FBVyxDQUFDLElBQUEsdUJBQVcsRUFBQyxPQUFPLENBQUMsRUFBRSxPQUFPLENBQUMsQ0FBQztRQUNwRCxDQUFDLENBQUMsQ0FBQztRQUVILEVBQUUsQ0FBQyxzQkFBc0IsRUFBRTtZQUN6QixNQUFNLENBQUMsV0FBVyxDQUFDLElBQUEsdUJBQVcsRUFBQyxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQztRQUMxQyxDQUFDLENBQUMsQ0FBQztJQUNMLENBQUMsQ0FBQyxDQUFDO0lBRUgsUUFBUSxDQUFDLG1CQUFtQixFQUFFO1FBQzVCLEVBQUUsQ0FBQyx3Q0FBd0MsRUFBRTtZQUMzQyxnREFBZ0Q7WUFDaEQsTUFBTSxHQUFHLEdBQUcsTUFBTSxDQUFDLElBQUksQ0FBQyxDQUFDLElBQUksRUFBRSxJQUFJLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQztZQUM1QyxNQUFNLENBQUMsV0FBVyxDQUFDLEdBQUcsQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLEVBQUUsTUFBTSxDQUFDLENBQUM7WUFDbkQsTUFBTSxDQUFDLFdBQVcsQ0FBQyxJQUFBLDZCQUFpQixFQUFDLEdBQUcsQ0FBQyxFQUFFLE1BQU0sQ0FBQyxDQUFDO1FBQ3JELENBQUMsQ0FBQyxDQUFDO1FBRUgsRUFBRSxDQUFDLDhDQUE4QyxFQUFFO1lBQ2pELE1BQU0sRUFBRSxHQUFHLElBQUksVUFBVSxDQUFDLENBQUMsSUFBSSxFQUFFLElBQUksRUFBRSxJQUFJLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQztZQUNyRCxNQUFNLENBQUMsV0FBVyxDQUFDLElBQUEsNkJBQWlCLEVBQUMsRUFBRSxDQUFDLEVBQUUsTUFBTSxDQUFDLENBQUM7UUFDcEQsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztJQUVILFFBQVEsQ0FBQyxtQkFBbUIsRUFBRTtRQUM1QixFQUFFLENBQUMsdUNBQXVDLEVBQUU7WUFDMUMsTUFBTSxRQUFRLEdBQUcsTUFBTSxDQUFDLElBQUksQ0FBQyxDQUFDLElBQUksRUFBRSxJQUFJLEVBQUUsSUFBSSxFQUFFLElBQUksRUFBRSxJQUFJLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQztZQUNuRSxNQUFNLE9BQU8sR0FBRyxJQUFBLDZCQUFpQixFQUFDLFFBQVEsQ0FBQyxDQUFDO1lBQzVDLE1BQU0sT0FBTyxHQUFHLElBQUEsNkJBQWlCLEVBQUMsT0FBTyxDQUFDLENBQUM7WUFDM0MsTUFBTSxDQUFDLGVBQWUsQ0FBQyxPQUFPLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDNUMsQ0FBQyxDQUFDLENBQUM7UUFFSCxFQUFFLENBQUMsc0NBQXNDLEVBQUU7WUFDekMsTUFBTSxPQUFPLEdBQUcsSUFBQSw2QkFBaUIsRUFBQyxNQUFNLENBQUMsQ0FBQztZQUMxQyxNQUFNLENBQUMsZUFBZSxDQUFDLE9BQU8sRUFBRSxNQUFNLENBQUMsSUFBSSxDQUFDLENBQUMsSUFBSSxFQUFFLElBQUksRUFBRSxJQUFJLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDbkUsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztBQUNMLENBQUMsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0ICogYXMgYXNzZXJ0IGZyb20gJ2Fzc2VydCc7XG5pbXBvcnQgeyBiYXNlNjRVcmxUb0J1ZmZlciwgYnVmZmVyVG9CYXNlNjRVcmwsIHRvQmFzZTY0VXJsIH0gZnJvbSAnLi4vLi4vc3JjL2Jhc2U2NHVybCc7XG5cbmRlc2NyaWJlKCdiYXNlNjR1cmwgaGVscGVycycsIGZ1bmN0aW9uICgpIHtcbiAgZGVzY3JpYmUoJ3RvQmFzZTY0VXJsJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdyZXBsYWNlcyArLCAvIGFuZCBzdHJpcHMgcGFkZGluZycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGFzc2VydC5zdHJpY3RFcXVhbCh0b0Jhc2U2NFVybCgnYStiL2M9PScpLCAnYS1iX2MnKTtcbiAgICB9KTtcblxuICAgIGl0KCdpcyBhIG5vLW9wIG9uIGFscmVhZHktYmFzZTY0dXJsIGlucHV0JywgZnVuY3Rpb24gKCkge1xuICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKHRvQmFzZTY0VXJsKCdhLWJfYycpLCAnYS1iX2MnKTtcbiAgICB9KTtcblxuICAgIGl0KCdoYW5kbGVzIGVtcHR5IHN0cmluZycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGFzc2VydC5zdHJpY3RFcXVhbCh0b0Jhc2U2NFVybCgnJyksICcnKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ2J1ZmZlclRvQmFzZTY0VXJsJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdlbmNvZGVzIGEgQnVmZmVyIHRvIHVucGFkZGVkIGJhc2U2NHVybCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIC8vIGJ5dGVzIHRoYXQgcHJvZHVjZSArIGFuZCAvIGluIHN0YW5kYXJkIGJhc2U2NFxuICAgICAgY29uc3QgYnVmID0gQnVmZmVyLmZyb20oWzB4ZmIsIDB4ZmYsIDB4YmZdKTtcbiAgICAgIGFzc2VydC5zdHJpY3RFcXVhbChidWYudG9TdHJpbmcoJ2Jhc2U2NCcpLCAnKy8rLycpO1xuICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKGJ1ZmZlclRvQmFzZTY0VXJsKGJ1ZiksICctXy1fJyk7XG4gICAgfSk7XG5cbiAgICBpdCgnZW5jb2RlcyBhbiBBcnJheUJ1ZmZlciB0byB1bnBhZGRlZCBiYXNlNjR1cmwnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBhYiA9IG5ldyBVaW50OEFycmF5KFsweGZmLCAweGZlLCAweGZkXSkuYnVmZmVyO1xuICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKGJ1ZmZlclRvQmFzZTY0VXJsKGFiKSwgJ19fNzknKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ2Jhc2U2NFVybFRvQnVmZmVyJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdyb3VuZC10cmlwcyB0aHJvdWdoIGJ1ZmZlclRvQmFzZTY0VXJsJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qgb3JpZ2luYWwgPSBCdWZmZXIuZnJvbShbMHgwMCwgMHhmZiwgMHgxMCwgMHgyMCwgMHhhYiwgMHhjZF0pO1xuICAgICAgY29uc3QgZW5jb2RlZCA9IGJ1ZmZlclRvQmFzZTY0VXJsKG9yaWdpbmFsKTtcbiAgICAgIGNvbnN0IGRlY29kZWQgPSBiYXNlNjRVcmxUb0J1ZmZlcihlbmNvZGVkKTtcbiAgICAgIGFzc2VydC5kZWVwU3RyaWN0RXF1YWwoZGVjb2RlZCwgb3JpZ2luYWwpO1xuICAgIH0pO1xuXG4gICAgaXQoJ2RlY29kZXMgYmFzZTY0dXJsIHdpdGggLSBhbmQgXyBjaGFycycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGRlY29kZWQgPSBiYXNlNjRVcmxUb0J1ZmZlcignLV8tXycpO1xuICAgICAgYXNzZXJ0LmRlZXBTdHJpY3RFcXVhbChkZWNvZGVkLCBCdWZmZXIuZnJvbShbMHhmYiwgMHhmZiwgMHhiZl0pKTtcbiAgICB9KTtcbiAgfSk7XG59KTtcbiJdfQ==
|
|
@@ -39,7 +39,10 @@ const src_1 = require("../../src");
|
|
|
39
39
|
const REAL_FIXTURE = {
|
|
40
40
|
basePrfSalt: 'ZqJ64M2dL65zn2-Jxd58SMN2ILc9QjbCFxUTGHd_LC8',
|
|
41
41
|
enterpriseId: '69c2aea1a3d7bc07f7f775c0ca86b0ec',
|
|
42
|
-
|
|
42
|
+
// base64url encoding of the HMAC-SHA256(baseSalt_decoded, enterpriseId) digest.
|
|
43
|
+
// Same encoding the server stores and the WebAuthn PRF extension consumes — keeping
|
|
44
|
+
// one encoding everywhere avoids the hex/base64url mismatch that broke browser PRF.
|
|
45
|
+
expectedDerivedSalt: 'oiasOqzkuyuEz_8043-3IXYghSu3LV4N_a1MLIRzmU8',
|
|
43
46
|
};
|
|
44
47
|
describe('deriveEnterpriseSalt', function () {
|
|
45
48
|
it('produces the correct derived salt for real fixture values', function () {
|
|
@@ -63,11 +66,12 @@ describe('deriveEnterpriseSalt', function () {
|
|
|
63
66
|
const saltB = (0, src_1.deriveEnterpriseSalt)('deadbeefcafebabe0102030405060708', REAL_FIXTURE.enterpriseId);
|
|
64
67
|
assert.notStrictEqual(saltA, saltB);
|
|
65
68
|
});
|
|
66
|
-
it('returns a non-empty
|
|
69
|
+
it('returns a non-empty unpadded base64url string', function () {
|
|
67
70
|
const result = (0, src_1.deriveEnterpriseSalt)(REAL_FIXTURE.basePrfSalt, REAL_FIXTURE.enterpriseId);
|
|
68
71
|
assert.strictEqual(typeof result, 'string');
|
|
69
72
|
assert.ok(result.length > 0);
|
|
70
|
-
|
|
73
|
+
// Base64url alphabet, no padding. SHA-256 = 32 bytes → 43 base64url chars.
|
|
74
|
+
assert.match(result, /^[A-Za-z0-9_-]{43}$/);
|
|
71
75
|
});
|
|
72
76
|
});
|
|
73
|
-
//# sourceMappingURL=data:application/json;base64,
|
|
77
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGVyaXZlRW50ZXJwcmlzZVNhbHQudGVzdC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3Rlc3QvdW5pdC9kZXJpdmVFbnRlcnByaXNlU2FsdC50ZXN0LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsK0NBQWlDO0FBQ2pDLG1DQUFpRDtBQUVqRCwrRUFBK0U7QUFDL0UsTUFBTSxZQUFZLEdBQUc7SUFDbkIsV0FBVyxFQUFFLDZDQUE2QztJQUMxRCxZQUFZLEVBQUUsa0NBQWtDO0lBQ2hELGdGQUFnRjtJQUNoRixvRkFBb0Y7SUFDcEYsb0ZBQW9GO0lBQ3BGLG1CQUFtQixFQUFFLDZDQUE2QztDQUNuRSxDQUFDO0FBRUYsUUFBUSxDQUFDLHNCQUFzQixFQUFFO0lBQy9CLEVBQUUsQ0FBQywyREFBMkQsRUFBRTtRQUM5RCwrRUFBK0U7UUFDL0UsbUVBQW1FO1FBQ25FLE1BQU0sQ0FBQyxXQUFXLENBQ2hCLElBQUEsMEJBQW9CLEVBQUMsWUFBWSxDQUFDLFdBQVcsRUFBRSxZQUFZLENBQUMsWUFBWSxDQUFDLEVBQ3pFLFlBQVksQ0FBQyxtQkFBbUIsQ0FDakMsQ0FBQztJQUNKLENBQUMsQ0FBQyxDQUFDO0lBRUgsRUFBRSxDQUFDLDZEQUE2RCxFQUFFO1FBQ2hFLE1BQU0sS0FBSyxHQUFHLElBQUEsMEJBQW9CLEVBQUMsWUFBWSxDQUFDLFdBQVcsRUFBRSxZQUFZLENBQUMsWUFBWSxDQUFDLENBQUM7UUFDeEYsTUFBTSxNQUFNLEdBQUcsSUFBQSwwQkFBb0IsRUFBQyxZQUFZLENBQUMsV0FBVyxFQUFFLFlBQVksQ0FBQyxZQUFZLENBQUMsQ0FBQztRQUN6RixNQUFNLENBQUMsRUFBRSxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBQ2pCLE1BQU0sQ0FBQyxXQUFXLENBQUMsS0FBSyxFQUFFLE1BQU0sQ0FBQyxDQUFDO0lBQ3BDLENBQUMsQ0FBQyxDQUFDO0lBRUgsRUFBRSxDQUFDLDRFQUE0RSxFQUFFO1FBQy9FLE1BQU0sS0FBSyxHQUFHLElBQUEsMEJBQW9CLEVBQUMsWUFBWSxDQUFDLFdBQVcsRUFBRSxZQUFZLENBQUMsWUFBWSxDQUFDLENBQUM7UUFDeEYsTUFBTSxLQUFLLEdBQUcsSUFBQSwwQkFBb0IsRUFBQyxZQUFZLENBQUMsV0FBVyxFQUFFLHlCQUF5QixDQUFDLENBQUM7UUFDeEYsTUFBTSxDQUFDLGNBQWMsQ0FBQyxLQUFLLEVBQUUsS0FBSyxDQUFDLENBQUM7SUFDdEMsQ0FBQyxDQUFDLENBQUM7SUFFSCxFQUFFLENBQUMsNEVBQTRFLEVBQUU7UUFDL0UsTUFBTSxLQUFLLEdBQUcsSUFBQSwwQkFBb0IsRUFBQyxZQUFZLENBQUMsV0FBVyxFQUFFLFlBQVksQ0FBQyxZQUFZLENBQUMsQ0FBQztRQUN4RixNQUFNLEtBQUssR0FBRyxJQUFBLDBCQUFvQixFQUFDLGtDQUFrQyxFQUFFLFlBQVksQ0FBQyxZQUFZLENBQUMsQ0FBQztRQUNsRyxNQUFNLENBQUMsY0FBYyxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsQ0FBQztJQUN0QyxDQUFDLENBQUMsQ0FBQztJQUVILEVBQUUsQ0FBQywrQ0FBK0MsRUFBRTtRQUNsRCxNQUFNLE1BQU0sR0FBRyxJQUFBLDBCQUFvQixFQUFDLFlBQVksQ0FBQyxXQUFXLEVBQUUsWUFBWSxDQUFDLFlBQVksQ0FBQyxDQUFDO1FBQ3pGLE1BQU0sQ0FBQyxXQUFXLENBQUMsT0FBTyxNQUFNLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDNUMsTUFBTSxDQUFDLEVBQUUsQ0FBQyxNQUFNLENBQUMsTUFBTSxHQUFHLENBQUMsQ0FBQyxDQUFDO1FBQzdCLDJFQUEyRTtRQUMzRSxNQUFNLENBQUMsS0FBSyxDQUFDLE1BQU0sRUFBRSxxQkFBcUIsQ0FBQyxDQUFDO0lBQzlDLENBQUMsQ0FBQyxDQUFDO0FBQ0wsQ0FBQyxDQUFDLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBhc3NlcnQgZnJvbSAnYXNzZXJ0JztcbmltcG9ydCB7IGRlcml2ZUVudGVycHJpc2VTYWx0IH0gZnJvbSAnLi4vLi4vc3JjJztcblxuLy8gUmVhbCBmaXh0dXJlIHZhbHVlcyBjYXB0dXJlZCBmcm9tIGEgbGl2ZSBlbnZpcm9ubWVudCAoREIgKyBicm93c2VyIGRldnRvb2xzKVxuY29uc3QgUkVBTF9GSVhUVVJFID0ge1xuICBiYXNlUHJmU2FsdDogJ1pxSjY0TTJkTDY1em4yLUp4ZDU4U01OMklMYzlRamJDRnhVVEdIZF9MQzgnLFxuICBlbnRlcnByaXNlSWQ6ICc2OWMyYWVhMWEzZDdiYzA3ZjdmNzc1YzBjYTg2YjBlYycsXG4gIC8vIGJhc2U2NHVybCBlbmNvZGluZyBvZiB0aGUgSE1BQy1TSEEyNTYoYmFzZVNhbHRfZGVjb2RlZCwgZW50ZXJwcmlzZUlkKSBkaWdlc3QuXG4gIC8vIFNhbWUgZW5jb2RpbmcgdGhlIHNlcnZlciBzdG9yZXMgYW5kIHRoZSBXZWJBdXRobiBQUkYgZXh0ZW5zaW9uIGNvbnN1bWVzIOKAlCBrZWVwaW5nXG4gIC8vIG9uZSBlbmNvZGluZyBldmVyeXdoZXJlIGF2b2lkcyB0aGUgaGV4L2Jhc2U2NHVybCBtaXNtYXRjaCB0aGF0IGJyb2tlIGJyb3dzZXIgUFJGLlxuICBleHBlY3RlZERlcml2ZWRTYWx0OiAnb2lhc09xemt1eXVFel84MDQzLTNJWFlnaFN1M0xWNE5fYTFNTElSem1VOCcsXG59O1xuXG5kZXNjcmliZSgnZGVyaXZlRW50ZXJwcmlzZVNhbHQnLCBmdW5jdGlvbiAoKSB7XG4gIGl0KCdwcm9kdWNlcyB0aGUgY29ycmVjdCBkZXJpdmVkIHNhbHQgZm9yIHJlYWwgZml4dHVyZSB2YWx1ZXMnLCBmdW5jdGlvbiAoKSB7XG4gICAgLy8gVmVyaWZpZXMgU0RLIG91dHB1dCBtYXRjaGVzIHdoYXQgdGhlIHJldGFpbCBVSSBwcm9kdWNlcyBmb3IgdGhlIHNhbWUgaW5wdXRzLFxuICAgIC8vIGVuc3VyaW5nIGNsaWVudHMgY2FuIG1vdmUgYmV0d2VlbiBTREsgYW5kIHJldGFpbCBhcHAgc2VhbWxlc3NseS5cbiAgICBhc3NlcnQuc3RyaWN0RXF1YWwoXG4gICAgICBkZXJpdmVFbnRlcnByaXNlU2FsdChSRUFMX0ZJWFRVUkUuYmFzZVByZlNhbHQsIFJFQUxfRklYVFVSRS5lbnRlcnByaXNlSWQpLFxuICAgICAgUkVBTF9GSVhUVVJFLmV4cGVjdGVkRGVyaXZlZFNhbHRcbiAgICApO1xuICB9KTtcblxuICBpdCgnaXMgZGV0ZXJtaW5pc3RpYyDigJQgc2FtZSBpbnB1dHMgYWx3YXlzIHByb2R1Y2UgdGhlIHNhbWUgc2FsdCcsIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCBmaXJzdCA9IGRlcml2ZUVudGVycHJpc2VTYWx0KFJFQUxfRklYVFVSRS5iYXNlUHJmU2FsdCwgUkVBTF9GSVhUVVJFLmVudGVycHJpc2VJZCk7XG4gICAgY29uc3Qgc2Vjb25kID0gZGVyaXZlRW50ZXJwcmlzZVNhbHQoUkVBTF9GSVhUVVJFLmJhc2VQcmZTYWx0LCBSRUFMX0ZJWFRVUkUuZW50ZXJwcmlzZUlkKTtcbiAgICBhc3NlcnQub2soZmlyc3QpO1xuICAgIGFzc2VydC5zdHJpY3RFcXVhbChmaXJzdCwgc2Vjb25kKTtcbiAgfSk7XG5cbiAgaXQoJ3Byb2R1Y2VzIGRpZmZlcmVudCBzYWx0cyBmb3IgZGlmZmVyZW50IGVudGVycHJpc2VJZHMgd2l0aCB0aGUgc2FtZSBwcmZTYWx0JywgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IHNhbHRBID0gZGVyaXZlRW50ZXJwcmlzZVNhbHQoUkVBTF9GSVhUVVJFLmJhc2VQcmZTYWx0LCBSRUFMX0ZJWFRVUkUuZW50ZXJwcmlzZUlkKTtcbiAgICBjb25zdCBzYWx0QiA9IGRlcml2ZUVudGVycHJpc2VTYWx0KFJFQUxfRklYVFVSRS5iYXNlUHJmU2FsdCwgJ2RpZmZlcmVudC1lbnRlcnByaXNlLWlkJyk7XG4gICAgYXNzZXJ0Lm5vdFN0cmljdEVxdWFsKHNhbHRBLCBzYWx0Qik7XG4gIH0pO1xuXG4gIGl0KCdwcm9kdWNlcyBkaWZmZXJlbnQgc2FsdHMgZm9yIGRpZmZlcmVudCBwcmZTYWx0cyB3aXRoIHRoZSBzYW1lIGVudGVycHJpc2VJZCcsIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCBzYWx0QSA9IGRlcml2ZUVudGVycHJpc2VTYWx0KFJFQUxfRklYVFVSRS5iYXNlUHJmU2FsdCwgUkVBTF9GSVhUVVJFLmVudGVycHJpc2VJZCk7XG4gICAgY29uc3Qgc2FsdEIgPSBkZXJpdmVFbnRlcnByaXNlU2FsdCgnZGVhZGJlZWZjYWZlYmFiZTAxMDIwMzA0MDUwNjA3MDgnLCBSRUFMX0ZJWFRVUkUuZW50ZXJwcmlzZUlkKTtcbiAgICBhc3NlcnQubm90U3RyaWN0RXF1YWwoc2FsdEEsIHNhbHRCKTtcbiAgfSk7XG5cbiAgaXQoJ3JldHVybnMgYSBub24tZW1wdHkgdW5wYWRkZWQgYmFzZTY0dXJsIHN0cmluZycsIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCByZXN1bHQgPSBkZXJpdmVFbnRlcnByaXNlU2FsdChSRUFMX0ZJWFRVUkUuYmFzZVByZlNhbHQsIFJFQUxfRklYVFVSRS5lbnRlcnByaXNlSWQpO1xuICAgIGFzc2VydC5zdHJpY3RFcXVhbCh0eXBlb2YgcmVzdWx0LCAnc3RyaW5nJyk7XG4gICAgYXNzZXJ0Lm9rKHJlc3VsdC5sZW5ndGggPiAwKTtcbiAgICAvLyBCYXNlNjR1cmwgYWxwaGFiZXQsIG5vIHBhZGRpbmcuIFNIQS0yNTYgPSAzMiBieXRlcyDihpIgNDMgYmFzZTY0dXJsIGNoYXJzLlxuICAgIGFzc2VydC5tYXRjaChyZXN1bHQsIC9eW0EtWmEtejAtOV8tXXs0M30kLyk7XG4gIH0pO1xufSk7XG4iXX0=
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"derivePasskeyPrfKey.test.d.ts","sourceRoot":"","sources":["../../../test/unit/derivePasskeyPrfKey.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
const assert = __importStar(require("assert"));
|
|
37
|
+
const sinon = __importStar(require("sinon"));
|
|
38
|
+
const derivePasskeyPrfKey_1 = require("../../src/derivePasskeyPrfKey");
|
|
39
|
+
describe('derivePasskeyPrfKey', function () {
|
|
40
|
+
const mockDevices = [
|
|
41
|
+
{
|
|
42
|
+
otpDeviceId: 'device-1',
|
|
43
|
+
authenticatorInfo: { credID: 'cred-aaa', fmt: 'none', publicKey: 'pk-1' },
|
|
44
|
+
prfSalt: 'salt-aaa',
|
|
45
|
+
encryptedPrv: 'enc-prv-1',
|
|
46
|
+
},
|
|
47
|
+
{
|
|
48
|
+
otpDeviceId: 'device-2',
|
|
49
|
+
authenticatorInfo: { credID: 'cred-bbb', fmt: 'none', publicKey: 'pk-2' },
|
|
50
|
+
prfSalt: 'salt-bbb',
|
|
51
|
+
encryptedPrv: 'enc-prv-2',
|
|
52
|
+
},
|
|
53
|
+
];
|
|
54
|
+
function makeWallet(devices) {
|
|
55
|
+
return {
|
|
56
|
+
getEncryptedUserKeychain: sinon.stub().resolves({
|
|
57
|
+
id: 'keychain-id',
|
|
58
|
+
pub: 'xpub123',
|
|
59
|
+
encryptedPrv: 'encrypted-prv',
|
|
60
|
+
type: 'independent',
|
|
61
|
+
webauthnDevices: devices,
|
|
62
|
+
}),
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
function makeBitGo(challenge = 'dGVzdC1jaGFsbGVuZ2U=') {
|
|
66
|
+
return {
|
|
67
|
+
url: sinon.stub().callsFake((path) => `https://app.bitgo.com/api/v2${path}`),
|
|
68
|
+
get: sinon.stub().returns({
|
|
69
|
+
result: sinon.stub().resolves({ challenge }),
|
|
70
|
+
}),
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
afterEach(function () {
|
|
74
|
+
sinon.restore();
|
|
75
|
+
});
|
|
76
|
+
it('should return a hex string on happy path', async function () {
|
|
77
|
+
const prfResult = new Uint8Array([0xde, 0xad, 0xbe, 0xef]).buffer;
|
|
78
|
+
const mockProvider = {
|
|
79
|
+
create: sinon.stub(),
|
|
80
|
+
get: sinon.stub().resolves({
|
|
81
|
+
prfResult,
|
|
82
|
+
credentialId: 'cred-aaa',
|
|
83
|
+
otpCode: 'otp-123',
|
|
84
|
+
}),
|
|
85
|
+
};
|
|
86
|
+
const wallet = makeWallet(mockDevices);
|
|
87
|
+
const mockBitGo = makeBitGo();
|
|
88
|
+
const result = await (0, derivePasskeyPrfKey_1.derivePasskeyPrfKey)({
|
|
89
|
+
bitgo: mockBitGo,
|
|
90
|
+
wallet: wallet,
|
|
91
|
+
provider: mockProvider,
|
|
92
|
+
});
|
|
93
|
+
// derivePassword converts ArrayBuffer to hex
|
|
94
|
+
assert.strictEqual(result, 'deadbeef');
|
|
95
|
+
assert.ok(mockProvider.get.calledOnce);
|
|
96
|
+
// Verify evalByCredential was passed
|
|
97
|
+
const getCallArgs = mockProvider.get.firstCall.args[0];
|
|
98
|
+
assert.strictEqual(getCallArgs.evalByCredential['cred-aaa'], 'salt-aaa');
|
|
99
|
+
assert.strictEqual(getCallArgs.evalByCredential['cred-bbb'], 'salt-bbb');
|
|
100
|
+
// Verify bitgo was used to fetch the assertion challenge
|
|
101
|
+
assert.ok(mockBitGo.get.calledOnce);
|
|
102
|
+
assert.ok(mockBitGo.url.calledWith('/user/otp/webauthn/auth', 2));
|
|
103
|
+
});
|
|
104
|
+
it("should throw 'No passkey devices available' when no devices", async function () {
|
|
105
|
+
const wallet = makeWallet(undefined);
|
|
106
|
+
const mockProvider = { create: sinon.stub(), get: sinon.stub() };
|
|
107
|
+
await assert.rejects(() => (0, derivePasskeyPrfKey_1.derivePasskeyPrfKey)({ bitgo: makeBitGo(), wallet: wallet, provider: mockProvider }), (err) => {
|
|
108
|
+
assert.strictEqual(err.message, 'No passkey devices available');
|
|
109
|
+
return true;
|
|
110
|
+
});
|
|
111
|
+
});
|
|
112
|
+
it("should throw 'No passkey devices available' when devices array is empty", async function () {
|
|
113
|
+
const wallet = makeWallet([]);
|
|
114
|
+
const mockProvider = { create: sinon.stub(), get: sinon.stub() };
|
|
115
|
+
await assert.rejects(() => (0, derivePasskeyPrfKey_1.derivePasskeyPrfKey)({ bitgo: makeBitGo(), wallet: wallet, provider: mockProvider }), (err) => {
|
|
116
|
+
assert.strictEqual(err.message, 'No passkey devices available');
|
|
117
|
+
return true;
|
|
118
|
+
});
|
|
119
|
+
});
|
|
120
|
+
it("should throw 'No passkey devices available with a valid PRF salt' when no device has prfSalt", async function () {
|
|
121
|
+
const devicesWithoutSalt = [
|
|
122
|
+
{
|
|
123
|
+
otpDeviceId: 'device-1',
|
|
124
|
+
authenticatorInfo: { credID: 'cred-aaa', fmt: 'none', publicKey: 'pk-1' },
|
|
125
|
+
prfSalt: '', // empty — buildEvalByCredential skips falsy prfSalt
|
|
126
|
+
encryptedPrv: 'enc-prv-1',
|
|
127
|
+
},
|
|
128
|
+
];
|
|
129
|
+
const wallet = makeWallet(devicesWithoutSalt);
|
|
130
|
+
const mockProvider = { create: sinon.stub(), get: sinon.stub() };
|
|
131
|
+
await assert.rejects(() => (0, derivePasskeyPrfKey_1.derivePasskeyPrfKey)({ bitgo: makeBitGo(), wallet: wallet, provider: mockProvider }), (err) => {
|
|
132
|
+
assert.strictEqual(err.message, 'No passkey devices available with a valid PRF salt');
|
|
133
|
+
return true;
|
|
134
|
+
});
|
|
135
|
+
});
|
|
136
|
+
it("should throw 'Could not identify which passkey device was used' when credentialId not found", async function () {
|
|
137
|
+
const mockProvider = {
|
|
138
|
+
create: sinon.stub(),
|
|
139
|
+
get: sinon.stub().resolves({
|
|
140
|
+
prfResult: new ArrayBuffer(32),
|
|
141
|
+
credentialId: 'unknown-cred-id',
|
|
142
|
+
otpCode: 'otp-123',
|
|
143
|
+
}),
|
|
144
|
+
};
|
|
145
|
+
const wallet = makeWallet(mockDevices);
|
|
146
|
+
await assert.rejects(() => (0, derivePasskeyPrfKey_1.derivePasskeyPrfKey)({ bitgo: makeBitGo(), wallet: wallet, provider: mockProvider }), (err) => {
|
|
147
|
+
assert.strictEqual(err.message, 'Could not identify which passkey device was used');
|
|
148
|
+
return true;
|
|
149
|
+
});
|
|
150
|
+
});
|
|
151
|
+
});
|
|
152
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGVyaXZlUGFzc2tleVByZktleS50ZXN0LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vdGVzdC91bml0L2Rlcml2ZVBhc3NrZXlQcmZLZXkudGVzdC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUFBLCtDQUFpQztBQUNqQyw2Q0FBK0I7QUFDL0IsdUVBQW9FO0FBRXBFLFFBQVEsQ0FBQyxxQkFBcUIsRUFBRTtJQUM5QixNQUFNLFdBQVcsR0FBRztRQUNsQjtZQUNFLFdBQVcsRUFBRSxVQUFVO1lBQ3ZCLGlCQUFpQixFQUFFLEVBQUUsTUFBTSxFQUFFLFVBQVUsRUFBRSxHQUFHLEVBQUUsTUFBZSxFQUFFLFNBQVMsRUFBRSxNQUFNLEVBQUU7WUFDbEYsT0FBTyxFQUFFLFVBQVU7WUFDbkIsWUFBWSxFQUFFLFdBQVc7U0FDMUI7UUFDRDtZQUNFLFdBQVcsRUFBRSxVQUFVO1lBQ3ZCLGlCQUFpQixFQUFFLEVBQUUsTUFBTSxFQUFFLFVBQVUsRUFBRSxHQUFHLEVBQUUsTUFBZSxFQUFFLFNBQVMsRUFBRSxNQUFNLEVBQUU7WUFDbEYsT0FBTyxFQUFFLFVBQVU7WUFDbkIsWUFBWSxFQUFFLFdBQVc7U0FDMUI7S0FDRixDQUFDO0lBRUYsU0FBUyxVQUFVLENBQUMsT0FBdUM7UUFDekQsT0FBTztZQUNMLHdCQUF3QixFQUFFLEtBQUssQ0FBQyxJQUFJLEVBQUUsQ0FBQyxRQUFRLENBQUM7Z0JBQzlDLEVBQUUsRUFBRSxhQUFhO2dCQUNqQixHQUFHLEVBQUUsU0FBUztnQkFDZCxZQUFZLEVBQUUsZUFBZTtnQkFDN0IsSUFBSSxFQUFFLGFBQWE7Z0JBQ25CLGVBQWUsRUFBRSxPQUFPO2FBQ3pCLENBQUM7U0FDSCxDQUFDO0lBQ0osQ0FBQztJQUVELFNBQVMsU0FBUyxDQUFDLFNBQVMsR0FBRyxzQkFBc0I7UUFDbkQsT0FBTztZQUNMLEdBQUcsRUFBRSxLQUFLLENBQUMsSUFBSSxFQUFFLENBQUMsU0FBUyxDQUFDLENBQUMsSUFBWSxFQUFFLEVBQUUsQ0FBQywrQkFBK0IsSUFBSSxFQUFFLENBQUM7WUFDcEYsR0FBRyxFQUFFLEtBQUssQ0FBQyxJQUFJLEVBQUUsQ0FBQyxPQUFPLENBQUM7Z0JBQ3hCLE1BQU0sRUFBRSxLQUFLLENBQUMsSUFBSSxFQUFFLENBQUMsUUFBUSxDQUFDLEVBQUUsU0FBUyxFQUFFLENBQUM7YUFDN0MsQ0FBQztTQUNILENBQUM7SUFDSixDQUFDO0lBRUQsU0FBUyxDQUFDO1FBQ1IsS0FBSyxDQUFDLE9BQU8sRUFBRSxDQUFDO0lBQ2xCLENBQUMsQ0FBQyxDQUFDO0lBRUgsRUFBRSxDQUFDLDBDQUEwQyxFQUFFLEtBQUs7UUFDbEQsTUFBTSxTQUFTLEdBQUcsSUFBSSxVQUFVLENBQUMsQ0FBQyxJQUFJLEVBQUUsSUFBSSxFQUFFLElBQUksRUFBRSxJQUFJLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQztRQUVsRSxNQUFNLFlBQVksR0FBRztZQUNuQixNQUFNLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRTtZQUNwQixHQUFHLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRSxDQUFDLFFBQVEsQ0FBQztnQkFDekIsU0FBUztnQkFDVCxZQUFZLEVBQUUsVUFBVTtnQkFDeEIsT0FBTyxFQUFFLFNBQVM7YUFDbkIsQ0FBQztTQUNILENBQUM7UUFFRixNQUFNLE1BQU0sR0FBRyxVQUFVLENBQUMsV0FBVyxDQUFDLENBQUM7UUFDdkMsTUFBTSxTQUFTLEdBQUcsU0FBUyxFQUFFLENBQUM7UUFFOUIsTUFBTSxNQUFNLEdBQUcsTUFBTSxJQUFBLHlDQUFtQixFQUFDO1lBQ3ZDLEtBQUssRUFBRSxTQUFnQjtZQUN2QixNQUFNLEVBQUUsTUFBYTtZQUNyQixRQUFRLEVBQUUsWUFBWTtTQUN2QixDQUFDLENBQUM7UUFFSCw2Q0FBNkM7UUFDN0MsTUFBTSxDQUFDLFdBQVcsQ0FBQyxNQUFNLEVBQUUsVUFBVSxDQUFDLENBQUM7UUFDdkMsTUFBTSxDQUFDLEVBQUUsQ0FBQyxZQUFZLENBQUMsR0FBRyxDQUFDLFVBQVUsQ0FBQyxDQUFDO1FBQ3ZDLHFDQUFxQztRQUNyQyxNQUFNLFdBQVcsR0FBRyxZQUFZLENBQUMsR0FBRyxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDdkQsTUFBTSxDQUFDLFdBQVcsQ0FBQyxXQUFXLENBQUMsZ0JBQWdCLENBQUMsVUFBVSxDQUFDLEVBQUUsVUFBVSxDQUFDLENBQUM7UUFDekUsTUFBTSxDQUFDLFdBQVcsQ0FBQyxXQUFXLENBQUMsZ0JBQWdCLENBQUMsVUFBVSxDQUFDLEVBQUUsVUFBVSxDQUFDLENBQUM7UUFDekUseURBQXlEO1FBQ3pELE1BQU0sQ0FBQyxFQUFFLENBQUMsU0FBUyxDQUFDLEdBQUcsQ0FBQyxVQUFVLENBQUMsQ0FBQztRQUNwQyxNQUFNLENBQUMsRUFBRSxDQUFDLFNBQVMsQ0FBQyxHQUFHLENBQUMsVUFBVSxDQUFDLHlCQUF5QixFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDcEUsQ0FBQyxDQUFDLENBQUM7SUFFSCxFQUFFLENBQUMsNkRBQTZELEVBQUUsS0FBSztRQUNyRSxNQUFNLE1BQU0sR0FBRyxVQUFVLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDckMsTUFBTSxZQUFZLEdBQUcsRUFBRSxNQUFNLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRSxFQUFFLEdBQUcsRUFBRSxLQUFLLENBQUMsSUFBSSxFQUFFLEVBQUUsQ0FBQztRQUVqRSxNQUFNLE1BQU0sQ0FBQyxPQUFPLENBQ2xCLEdBQUcsRUFBRSxDQUFDLElBQUEseUNBQW1CLEVBQUMsRUFBRSxLQUFLLEVBQUUsU0FBUyxFQUFTLEVBQUUsTUFBTSxFQUFFLE1BQWEsRUFBRSxRQUFRLEVBQUUsWUFBWSxFQUFFLENBQUMsRUFDdkcsQ0FBQyxHQUFVLEVBQUUsRUFBRTtZQUNiLE1BQU0sQ0FBQyxXQUFXLENBQUMsR0FBRyxDQUFDLE9BQU8sRUFBRSw4QkFBOEIsQ0FBQyxDQUFDO1lBQ2hFLE9BQU8sSUFBSSxDQUFDO1FBQ2QsQ0FBQyxDQUNGLENBQUM7SUFDSixDQUFDLENBQUMsQ0FBQztJQUVILEVBQUUsQ0FBQyx5RUFBeUUsRUFBRSxLQUFLO1FBQ2pGLE1BQU0sTUFBTSxHQUFHLFVBQVUsQ0FBQyxFQUFTLENBQUMsQ0FBQztRQUNyQyxNQUFNLFlBQVksR0FBRyxFQUFFLE1BQU0sRUFBRSxLQUFLLENBQUMsSUFBSSxFQUFFLEVBQUUsR0FBRyxFQUFFLEtBQUssQ0FBQyxJQUFJLEVBQUUsRUFBRSxDQUFDO1FBRWpFLE1BQU0sTUFBTSxDQUFDLE9BQU8sQ0FDbEIsR0FBRyxFQUFFLENBQUMsSUFBQSx5Q0FBbUIsRUFBQyxFQUFFLEtBQUssRUFBRSxTQUFTLEVBQVMsRUFBRSxNQUFNLEVBQUUsTUFBYSxFQUFFLFFBQVEsRUFBRSxZQUFZLEVBQUUsQ0FBQyxFQUN2RyxDQUFDLEdBQVUsRUFBRSxFQUFFO1lBQ2IsTUFBTSxDQUFDLFdBQVcsQ0FBQyxHQUFHLENBQUMsT0FBTyxFQUFFLDhCQUE4QixDQUFDLENBQUM7WUFDaEUsT0FBTyxJQUFJLENBQUM7UUFDZCxDQUFDLENBQ0YsQ0FBQztJQUNKLENBQUMsQ0FBQyxDQUFDO0lBRUgsRUFBRSxDQUFDLDhGQUE4RixFQUFFLEtBQUs7UUFDdEcsTUFBTSxrQkFBa0IsR0FBRztZQUN6QjtnQkFDRSxXQUFXLEVBQUUsVUFBVTtnQkFDdkIsaUJBQWlCLEVBQUUsRUFBRSxNQUFNLEVBQUUsVUFBVSxFQUFFLEdBQUcsRUFBRSxNQUFlLEVBQUUsU0FBUyxFQUFFLE1BQU0sRUFBRTtnQkFDbEYsT0FBTyxFQUFFLEVBQUUsRUFBRSxvREFBb0Q7Z0JBQ2pFLFlBQVksRUFBRSxXQUFXO2FBQzFCO1NBQ0YsQ0FBQztRQUVGLE1BQU0sTUFBTSxHQUFHLFVBQVUsQ0FBQyxrQkFBeUIsQ0FBQyxDQUFDO1FBQ3JELE1BQU0sWUFBWSxHQUFHLEVBQUUsTUFBTSxFQUFFLEtBQUssQ0FBQyxJQUFJLEVBQUUsRUFBRSxHQUFHLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRSxFQUFFLENBQUM7UUFFakUsTUFBTSxNQUFNLENBQUMsT0FBTyxDQUNsQixHQUFHLEVBQUUsQ0FBQyxJQUFBLHlDQUFtQixFQUFDLEVBQUUsS0FBSyxFQUFFLFNBQVMsRUFBUyxFQUFFLE1BQU0sRUFBRSxNQUFhLEVBQUUsUUFBUSxFQUFFLFlBQVksRUFBRSxDQUFDLEVBQ3ZHLENBQUMsR0FBVSxFQUFFLEVBQUU7WUFDYixNQUFNLENBQUMsV0FBVyxDQUFDLEdBQUcsQ0FBQyxPQUFPLEVBQUUsb0RBQW9ELENBQUMsQ0FBQztZQUN0RixPQUFPLElBQUksQ0FBQztRQUNkLENBQUMsQ0FDRixDQUFDO0lBQ0osQ0FBQyxDQUFDLENBQUM7SUFFSCxFQUFFLENBQUMsNkZBQTZGLEVBQUUsS0FBSztRQUNyRyxNQUFNLFlBQVksR0FBRztZQUNuQixNQUFNLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRTtZQUNwQixHQUFHLEVBQUUsS0FBSyxDQUFDLElBQUksRUFBRSxDQUFDLFFBQVEsQ0FBQztnQkFDekIsU0FBUyxFQUFFLElBQUksV0FBVyxDQUFDLEVBQUUsQ0FBQztnQkFDOUIsWUFBWSxFQUFFLGlCQUFpQjtnQkFDL0IsT0FBTyxFQUFFLFNBQVM7YUFDbkIsQ0FBQztTQUNILENBQUM7UUFFRixNQUFNLE1BQU0sR0FBRyxVQUFVLENBQUMsV0FBVyxDQUFDLENBQUM7UUFFdkMsTUFBTSxNQUFNLENBQUMsT0FBTyxDQUNsQixHQUFHLEVBQUUsQ0FBQyxJQUFBLHlDQUFtQixFQUFDLEVBQUUsS0FBSyxFQUFFLFNBQVMsRUFBUyxFQUFFLE1BQU0sRUFBRSxNQUFhLEVBQUUsUUFBUSxFQUFFLFlBQVksRUFBRSxDQUFDLEVBQ3ZHLENBQUMsR0FBVSxFQUFFLEVBQUU7WUFDYixNQUFNLENBQUMsV0FBVyxDQUFDLEdBQUcsQ0FBQyxPQUFPLEVBQUUsa0RBQWtELENBQUMsQ0FBQztZQUNwRixPQUFPLElBQUksQ0FBQztRQUNkLENBQUMsQ0FDRixDQUFDO0lBQ0osQ0FBQyxDQUFDLENBQUM7QUFDTCxDQUFDLENBQUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCAqIGFzIGFzc2VydCBmcm9tICdhc3NlcnQnO1xuaW1wb3J0ICogYXMgc2lub24gZnJvbSAnc2lub24nO1xuaW1wb3J0IHsgZGVyaXZlUGFzc2tleVByZktleSB9IGZyb20gJy4uLy4uL3NyYy9kZXJpdmVQYXNza2V5UHJmS2V5JztcblxuZGVzY3JpYmUoJ2Rlcml2ZVBhc3NrZXlQcmZLZXknLCBmdW5jdGlvbiAoKSB7XG4gIGNvbnN0IG1vY2tEZXZpY2VzID0gW1xuICAgIHtcbiAgICAgIG90cERldmljZUlkOiAnZGV2aWNlLTEnLFxuICAgICAgYXV0aGVudGljYXRvckluZm86IHsgY3JlZElEOiAnY3JlZC1hYWEnLCBmbXQ6ICdub25lJyBhcyBjb25zdCwgcHVibGljS2V5OiAncGstMScgfSxcbiAgICAgIHByZlNhbHQ6ICdzYWx0LWFhYScsXG4gICAgICBlbmNyeXB0ZWRQcnY6ICdlbmMtcHJ2LTEnLFxuICAgIH0sXG4gICAge1xuICAgICAgb3RwRGV2aWNlSWQ6ICdkZXZpY2UtMicsXG4gICAgICBhdXRoZW50aWNhdG9ySW5mbzogeyBjcmVkSUQ6ICdjcmVkLWJiYicsIGZtdDogJ25vbmUnIGFzIGNvbnN0LCBwdWJsaWNLZXk6ICdway0yJyB9LFxuICAgICAgcHJmU2FsdDogJ3NhbHQtYmJiJyxcbiAgICAgIGVuY3J5cHRlZFBydjogJ2VuYy1wcnYtMicsXG4gICAgfSxcbiAgXTtcblxuICBmdW5jdGlvbiBtYWtlV2FsbGV0KGRldmljZXM6IHR5cGVvZiBtb2NrRGV2aWNlcyB8IHVuZGVmaW5lZCkge1xuICAgIHJldHVybiB7XG4gICAgICBnZXRFbmNyeXB0ZWRVc2VyS2V5Y2hhaW46IHNpbm9uLnN0dWIoKS5yZXNvbHZlcyh7XG4gICAgICAgIGlkOiAna2V5Y2hhaW4taWQnLFxuICAgICAgICBwdWI6ICd4cHViMTIzJyxcbiAgICAgICAgZW5jcnlwdGVkUHJ2OiAnZW5jcnlwdGVkLXBydicsXG4gICAgICAgIHR5cGU6ICdpbmRlcGVuZGVudCcsXG4gICAgICAgIHdlYmF1dGhuRGV2aWNlczogZGV2aWNlcyxcbiAgICAgIH0pLFxuICAgIH07XG4gIH1cblxuICBmdW5jdGlvbiBtYWtlQml0R28oY2hhbGxlbmdlID0gJ2RHVnpkQzFqYUdGc2JHVnVaMlU9Jykge1xuICAgIHJldHVybiB7XG4gICAgICB1cmw6IHNpbm9uLnN0dWIoKS5jYWxsc0Zha2UoKHBhdGg6IHN0cmluZykgPT4gYGh0dHBzOi8vYXBwLmJpdGdvLmNvbS9hcGkvdjIke3BhdGh9YCksXG4gICAgICBnZXQ6IHNpbm9uLnN0dWIoKS5yZXR1cm5zKHtcbiAgICAgICAgcmVzdWx0OiBzaW5vbi5zdHViKCkucmVzb2x2ZXMoeyBjaGFsbGVuZ2UgfSksXG4gICAgICB9KSxcbiAgICB9O1xuICB9XG5cbiAgYWZ0ZXJFYWNoKGZ1bmN0aW9uICgpIHtcbiAgICBzaW5vbi5yZXN0b3JlKCk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgcmV0dXJuIGEgaGV4IHN0cmluZyBvbiBoYXBweSBwYXRoJywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IHByZlJlc3VsdCA9IG5ldyBVaW50OEFycmF5KFsweGRlLCAweGFkLCAweGJlLCAweGVmXSkuYnVmZmVyO1xuXG4gICAgY29uc3QgbW9ja1Byb3ZpZGVyID0ge1xuICAgICAgY3JlYXRlOiBzaW5vbi5zdHViKCksXG4gICAgICBnZXQ6IHNpbm9uLnN0dWIoKS5yZXNvbHZlcyh7XG4gICAgICAgIHByZlJlc3VsdCxcbiAgICAgICAgY3JlZGVudGlhbElkOiAnY3JlZC1hYWEnLFxuICAgICAgICBvdHBDb2RlOiAnb3RwLTEyMycsXG4gICAgICB9KSxcbiAgICB9O1xuXG4gICAgY29uc3Qgd2FsbGV0ID0gbWFrZVdhbGxldChtb2NrRGV2aWNlcyk7XG4gICAgY29uc3QgbW9ja0JpdEdvID0gbWFrZUJpdEdvKCk7XG5cbiAgICBjb25zdCByZXN1bHQgPSBhd2FpdCBkZXJpdmVQYXNza2V5UHJmS2V5KHtcbiAgICAgIGJpdGdvOiBtb2NrQml0R28gYXMgYW55LFxuICAgICAgd2FsbGV0OiB3YWxsZXQgYXMgYW55LFxuICAgICAgcHJvdmlkZXI6IG1vY2tQcm92aWRlcixcbiAgICB9KTtcblxuICAgIC8vIGRlcml2ZVBhc3N3b3JkIGNvbnZlcnRzIEFycmF5QnVmZmVyIHRvIGhleFxuICAgIGFzc2VydC5zdHJpY3RFcXVhbChyZXN1bHQsICdkZWFkYmVlZicpO1xuICAgIGFzc2VydC5vayhtb2NrUHJvdmlkZXIuZ2V0LmNhbGxlZE9uY2UpO1xuICAgIC8vIFZlcmlmeSBldmFsQnlDcmVkZW50aWFsIHdhcyBwYXNzZWRcbiAgICBjb25zdCBnZXRDYWxsQXJncyA9IG1vY2tQcm92aWRlci5nZXQuZmlyc3RDYWxsLmFyZ3NbMF07XG4gICAgYXNzZXJ0LnN0cmljdEVxdWFsKGdldENhbGxBcmdzLmV2YWxCeUNyZWRlbnRpYWxbJ2NyZWQtYWFhJ10sICdzYWx0LWFhYScpO1xuICAgIGFzc2VydC5zdHJpY3RFcXVhbChnZXRDYWxsQXJncy5ldmFsQnlDcmVkZW50aWFsWydjcmVkLWJiYiddLCAnc2FsdC1iYmInKTtcbiAgICAvLyBWZXJpZnkgYml0Z28gd2FzIHVzZWQgdG8gZmV0Y2ggdGhlIGFzc2VydGlvbiBjaGFsbGVuZ2VcbiAgICBhc3NlcnQub2sobW9ja0JpdEdvLmdldC5jYWxsZWRPbmNlKTtcbiAgICBhc3NlcnQub2sobW9ja0JpdEdvLnVybC5jYWxsZWRXaXRoKCcvdXNlci9vdHAvd2ViYXV0aG4vYXV0aCcsIDIpKTtcbiAgfSk7XG5cbiAgaXQoXCJzaG91bGQgdGhyb3cgJ05vIHBhc3NrZXkgZGV2aWNlcyBhdmFpbGFibGUnIHdoZW4gbm8gZGV2aWNlc1wiLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgY29uc3Qgd2FsbGV0ID0gbWFrZVdhbGxldCh1bmRlZmluZWQpO1xuICAgIGNvbnN0IG1vY2tQcm92aWRlciA9IHsgY3JlYXRlOiBzaW5vbi5zdHViKCksIGdldDogc2lub24uc3R1YigpIH07XG5cbiAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICgpID0+IGRlcml2ZVBhc3NrZXlQcmZLZXkoeyBiaXRnbzogbWFrZUJpdEdvKCkgYXMgYW55LCB3YWxsZXQ6IHdhbGxldCBhcyBhbnksIHByb3ZpZGVyOiBtb2NrUHJvdmlkZXIgfSksXG4gICAgICAoZXJyOiBFcnJvcikgPT4ge1xuICAgICAgICBhc3NlcnQuc3RyaWN0RXF1YWwoZXJyLm1lc3NhZ2UsICdObyBwYXNza2V5IGRldmljZXMgYXZhaWxhYmxlJyk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgICk7XG4gIH0pO1xuXG4gIGl0KFwic2hvdWxkIHRocm93ICdObyBwYXNza2V5IGRldmljZXMgYXZhaWxhYmxlJyB3aGVuIGRldmljZXMgYXJyYXkgaXMgZW1wdHlcIiwgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IHdhbGxldCA9IG1ha2VXYWxsZXQoW10gYXMgYW55KTtcbiAgICBjb25zdCBtb2NrUHJvdmlkZXIgPSB7IGNyZWF0ZTogc2lub24uc3R1YigpLCBnZXQ6IHNpbm9uLnN0dWIoKSB9O1xuXG4gICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoXG4gICAgICAoKSA9PiBkZXJpdmVQYXNza2V5UHJmS2V5KHsgYml0Z286IG1ha2VCaXRHbygpIGFzIGFueSwgd2FsbGV0OiB3YWxsZXQgYXMgYW55LCBwcm92aWRlcjogbW9ja1Byb3ZpZGVyIH0pLFxuICAgICAgKGVycjogRXJyb3IpID0+IHtcbiAgICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKGVyci5tZXNzYWdlLCAnTm8gcGFzc2tleSBkZXZpY2VzIGF2YWlsYWJsZScpO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICApO1xuICB9KTtcblxuICBpdChcInNob3VsZCB0aHJvdyAnTm8gcGFzc2tleSBkZXZpY2VzIGF2YWlsYWJsZSB3aXRoIGEgdmFsaWQgUFJGIHNhbHQnIHdoZW4gbm8gZGV2aWNlIGhhcyBwcmZTYWx0XCIsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCBkZXZpY2VzV2l0aG91dFNhbHQgPSBbXG4gICAgICB7XG4gICAgICAgIG90cERldmljZUlkOiAnZGV2aWNlLTEnLFxuICAgICAgICBhdXRoZW50aWNhdG9ySW5mbzogeyBjcmVkSUQ6ICdjcmVkLWFhYScsIGZtdDogJ25vbmUnIGFzIGNvbnN0LCBwdWJsaWNLZXk6ICdway0xJyB9LFxuICAgICAgICBwcmZTYWx0OiAnJywgLy8gZW1wdHkg4oCUIGJ1aWxkRXZhbEJ5Q3JlZGVudGlhbCBza2lwcyBmYWxzeSBwcmZTYWx0XG4gICAgICAgIGVuY3J5cHRlZFBydjogJ2VuYy1wcnYtMScsXG4gICAgICB9LFxuICAgIF07XG5cbiAgICBjb25zdCB3YWxsZXQgPSBtYWtlV2FsbGV0KGRldmljZXNXaXRob3V0U2FsdCBhcyBhbnkpO1xuICAgIGNvbnN0IG1vY2tQcm92aWRlciA9IHsgY3JlYXRlOiBzaW5vbi5zdHViKCksIGdldDogc2lub24uc3R1YigpIH07XG5cbiAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICgpID0+IGRlcml2ZVBhc3NrZXlQcmZLZXkoeyBiaXRnbzogbWFrZUJpdEdvKCkgYXMgYW55LCB3YWxsZXQ6IHdhbGxldCBhcyBhbnksIHByb3ZpZGVyOiBtb2NrUHJvdmlkZXIgfSksXG4gICAgICAoZXJyOiBFcnJvcikgPT4ge1xuICAgICAgICBhc3NlcnQuc3RyaWN0RXF1YWwoZXJyLm1lc3NhZ2UsICdObyBwYXNza2V5IGRldmljZXMgYXZhaWxhYmxlIHdpdGggYSB2YWxpZCBQUkYgc2FsdCcpO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICApO1xuICB9KTtcblxuICBpdChcInNob3VsZCB0aHJvdyAnQ291bGQgbm90IGlkZW50aWZ5IHdoaWNoIHBhc3NrZXkgZGV2aWNlIHdhcyB1c2VkJyB3aGVuIGNyZWRlbnRpYWxJZCBub3QgZm91bmRcIiwgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IG1vY2tQcm92aWRlciA9IHtcbiAgICAgIGNyZWF0ZTogc2lub24uc3R1YigpLFxuICAgICAgZ2V0OiBzaW5vbi5zdHViKCkucmVzb2x2ZXMoe1xuICAgICAgICBwcmZSZXN1bHQ6IG5ldyBBcnJheUJ1ZmZlcigzMiksXG4gICAgICAgIGNyZWRlbnRpYWxJZDogJ3Vua25vd24tY3JlZC1pZCcsXG4gICAgICAgIG90cENvZGU6ICdvdHAtMTIzJyxcbiAgICAgIH0pLFxuICAgIH07XG5cbiAgICBjb25zdCB3YWxsZXQgPSBtYWtlV2FsbGV0KG1vY2tEZXZpY2VzKTtcblxuICAgIGF3YWl0IGFzc2VydC5yZWplY3RzKFxuICAgICAgKCkgPT4gZGVyaXZlUGFzc2tleVByZktleSh7IGJpdGdvOiBtYWtlQml0R28oKSBhcyBhbnksIHdhbGxldDogd2FsbGV0IGFzIGFueSwgcHJvdmlkZXI6IG1vY2tQcm92aWRlciB9KSxcbiAgICAgIChlcnI6IEVycm9yKSA9PiB7XG4gICAgICAgIGFzc2VydC5zdHJpY3RFcXVhbChlcnIubWVzc2FnZSwgJ0NvdWxkIG5vdCBpZGVudGlmeSB3aGljaCBwYXNza2V5IGRldmljZSB3YXMgdXNlZCcpO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICApO1xuICB9KTtcbn0pO1xuIl19
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"registerPasskey.test.d.ts","sourceRoot":"","sources":["../../../test/unit/registerPasskey.test.ts"],"names":[],"mappings":""}
|