@technomoron/api-server-base 2.0.0-beta.5 → 2.0.0-beta.7
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.
|
@@ -34,6 +34,26 @@ function toBuffer(value) {
|
|
|
34
34
|
const view = value instanceof Uint8Array ? value : new Uint8Array(value);
|
|
35
35
|
return Buffer.from(view);
|
|
36
36
|
}
|
|
37
|
+
function toBufferOrNull(value) {
|
|
38
|
+
if (!value) {
|
|
39
|
+
return null;
|
|
40
|
+
}
|
|
41
|
+
if (Buffer.isBuffer(value)) {
|
|
42
|
+
return value;
|
|
43
|
+
}
|
|
44
|
+
if (value instanceof ArrayBuffer || value instanceof Uint8Array) {
|
|
45
|
+
return toBuffer(value);
|
|
46
|
+
}
|
|
47
|
+
if (typeof value === 'string') {
|
|
48
|
+
try {
|
|
49
|
+
return fromBase64Url(value);
|
|
50
|
+
}
|
|
51
|
+
catch {
|
|
52
|
+
return null;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
return null;
|
|
56
|
+
}
|
|
37
57
|
class PasskeyService {
|
|
38
58
|
constructor(config, adapter, logger = console) {
|
|
39
59
|
this.config = config;
|
|
@@ -170,11 +190,24 @@ class PasskeyService {
|
|
|
170
190
|
return { verified: false };
|
|
171
191
|
}
|
|
172
192
|
const registrationInfo = result.registrationInfo;
|
|
193
|
+
const attestationResponse = params.response?.response;
|
|
194
|
+
const credentialIdPrimary = toBufferOrNull(registrationInfo.credentialID);
|
|
195
|
+
const credentialIdFallback = toBufferOrNull(params.response?.id);
|
|
196
|
+
const credentialId = credentialIdPrimary && credentialIdPrimary.length > 0 ? credentialIdPrimary : credentialIdFallback;
|
|
197
|
+
const publicKeyPrimary = toBufferOrNull(registrationInfo.credentialPublicKey);
|
|
198
|
+
const publicKeyFallback = toBufferOrNull(attestationResponse?.publicKey);
|
|
199
|
+
const publicKey = publicKeyPrimary && publicKeyPrimary.length > 0 ? publicKeyPrimary : publicKeyFallback;
|
|
200
|
+
if (!credentialId || credentialId.length === 0) {
|
|
201
|
+
return { verified: false, message: 'Missing credential id in registration response' };
|
|
202
|
+
}
|
|
203
|
+
if (!publicKey || publicKey.length === 0) {
|
|
204
|
+
return { verified: false, message: 'Missing public key in registration response' };
|
|
205
|
+
}
|
|
173
206
|
await this.adapter.saveCredential({
|
|
174
207
|
userId: user.id,
|
|
175
|
-
credentialId
|
|
176
|
-
publicKey
|
|
177
|
-
counter: registrationInfo.counter,
|
|
208
|
+
credentialId,
|
|
209
|
+
publicKey,
|
|
210
|
+
counter: registrationInfo.counter ?? 0,
|
|
178
211
|
transports: sanitizeTransports(params.response.transports),
|
|
179
212
|
backedUp: registrationInfo.credentialDeviceType === 'multiDevice',
|
|
180
213
|
deviceType: registrationInfo.credentialDeviceType
|
|
@@ -194,19 +227,19 @@ class PasskeyService {
|
|
|
194
227
|
}
|
|
195
228
|
const user = await this.requireUser({ userId: credential.userId, login: record.login });
|
|
196
229
|
const storedAuthData = {
|
|
197
|
-
|
|
230
|
+
id: credential.credentialId,
|
|
231
|
+
publicKey: credential.publicKey,
|
|
198
232
|
counter: credential.counter,
|
|
233
|
+
transports: credential.transports ?? undefined,
|
|
199
234
|
credentialBackedUp: credential.backedUp,
|
|
200
|
-
credentialDeviceType: credential.deviceType
|
|
201
|
-
credentialPublicKey: credential.publicKey,
|
|
202
|
-
transports: credential.transports ?? undefined
|
|
235
|
+
credentialDeviceType: credential.deviceType
|
|
203
236
|
};
|
|
204
237
|
const result = await (0, server_1.verifyAuthenticationResponse)({
|
|
205
238
|
response,
|
|
206
239
|
expectedChallenge: record.challenge,
|
|
207
240
|
expectedOrigin: this.config.origins,
|
|
208
241
|
expectedRPID: this.config.rpId,
|
|
209
|
-
|
|
242
|
+
credential: storedAuthData,
|
|
210
243
|
requireUserVerification: true
|
|
211
244
|
});
|
|
212
245
|
if (!result.verified) {
|
|
@@ -31,6 +31,26 @@ function toBuffer(value) {
|
|
|
31
31
|
const view = value instanceof Uint8Array ? value : new Uint8Array(value);
|
|
32
32
|
return Buffer.from(view);
|
|
33
33
|
}
|
|
34
|
+
function toBufferOrNull(value) {
|
|
35
|
+
if (!value) {
|
|
36
|
+
return null;
|
|
37
|
+
}
|
|
38
|
+
if (Buffer.isBuffer(value)) {
|
|
39
|
+
return value;
|
|
40
|
+
}
|
|
41
|
+
if (value instanceof ArrayBuffer || value instanceof Uint8Array) {
|
|
42
|
+
return toBuffer(value);
|
|
43
|
+
}
|
|
44
|
+
if (typeof value === 'string') {
|
|
45
|
+
try {
|
|
46
|
+
return fromBase64Url(value);
|
|
47
|
+
}
|
|
48
|
+
catch {
|
|
49
|
+
return null;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
return null;
|
|
53
|
+
}
|
|
34
54
|
export class PasskeyService {
|
|
35
55
|
constructor(config, adapter, logger = console) {
|
|
36
56
|
this.config = config;
|
|
@@ -167,11 +187,24 @@ export class PasskeyService {
|
|
|
167
187
|
return { verified: false };
|
|
168
188
|
}
|
|
169
189
|
const registrationInfo = result.registrationInfo;
|
|
190
|
+
const attestationResponse = params.response?.response;
|
|
191
|
+
const credentialIdPrimary = toBufferOrNull(registrationInfo.credentialID);
|
|
192
|
+
const credentialIdFallback = toBufferOrNull(params.response?.id);
|
|
193
|
+
const credentialId = credentialIdPrimary && credentialIdPrimary.length > 0 ? credentialIdPrimary : credentialIdFallback;
|
|
194
|
+
const publicKeyPrimary = toBufferOrNull(registrationInfo.credentialPublicKey);
|
|
195
|
+
const publicKeyFallback = toBufferOrNull(attestationResponse?.publicKey);
|
|
196
|
+
const publicKey = publicKeyPrimary && publicKeyPrimary.length > 0 ? publicKeyPrimary : publicKeyFallback;
|
|
197
|
+
if (!credentialId || credentialId.length === 0) {
|
|
198
|
+
return { verified: false, message: 'Missing credential id in registration response' };
|
|
199
|
+
}
|
|
200
|
+
if (!publicKey || publicKey.length === 0) {
|
|
201
|
+
return { verified: false, message: 'Missing public key in registration response' };
|
|
202
|
+
}
|
|
170
203
|
await this.adapter.saveCredential({
|
|
171
204
|
userId: user.id,
|
|
172
|
-
credentialId
|
|
173
|
-
publicKey
|
|
174
|
-
counter: registrationInfo.counter,
|
|
205
|
+
credentialId,
|
|
206
|
+
publicKey,
|
|
207
|
+
counter: registrationInfo.counter ?? 0,
|
|
175
208
|
transports: sanitizeTransports(params.response.transports),
|
|
176
209
|
backedUp: registrationInfo.credentialDeviceType === 'multiDevice',
|
|
177
210
|
deviceType: registrationInfo.credentialDeviceType
|
|
@@ -191,19 +224,19 @@ export class PasskeyService {
|
|
|
191
224
|
}
|
|
192
225
|
const user = await this.requireUser({ userId: credential.userId, login: record.login });
|
|
193
226
|
const storedAuthData = {
|
|
194
|
-
|
|
227
|
+
id: credential.credentialId,
|
|
228
|
+
publicKey: credential.publicKey,
|
|
195
229
|
counter: credential.counter,
|
|
230
|
+
transports: credential.transports ?? undefined,
|
|
196
231
|
credentialBackedUp: credential.backedUp,
|
|
197
|
-
credentialDeviceType: credential.deviceType
|
|
198
|
-
credentialPublicKey: credential.publicKey,
|
|
199
|
-
transports: credential.transports ?? undefined
|
|
232
|
+
credentialDeviceType: credential.deviceType
|
|
200
233
|
};
|
|
201
234
|
const result = await verifyAuthenticationResponse({
|
|
202
235
|
response,
|
|
203
236
|
expectedChallenge: record.challenge,
|
|
204
237
|
expectedOrigin: this.config.origins,
|
|
205
238
|
expectedRPID: this.config.rpId,
|
|
206
|
-
|
|
239
|
+
credential: storedAuthData,
|
|
207
240
|
requireUserVerification: true
|
|
208
241
|
});
|
|
209
242
|
if (!result.verified) {
|