diff options
Diffstat (limited to 'packages/server/src')
-rw-r--r-- | packages/server/src/authentication/generateAuthenticationOptions.test.ts | 38 | ||||
-rw-r--r-- | packages/server/src/authentication/generateAuthenticationOptions.ts | 23 |
2 files changed, 34 insertions, 27 deletions
diff --git a/packages/server/src/authentication/generateAuthenticationOptions.test.ts b/packages/server/src/authentication/generateAuthenticationOptions.test.ts index 7acb250..49d668e 100644 --- a/packages/server/src/authentication/generateAuthenticationOptions.test.ts +++ b/packages/server/src/authentication/generateAuthenticationOptions.test.ts @@ -11,13 +11,11 @@ Deno.test('should generate credential request options suitable for sending via J const options = await generateAuthenticationOptions({ allowCredentials: [ { - id: isoUint8Array.fromASCIIString('1234'), - type: 'public-key', + id: '1234', transports: ['usb', 'nfc'], }, { - id: isoUint8Array.fromASCIIString('5678'), - type: 'public-key', + id: '5678', transports: ['internal'], }, ], @@ -30,12 +28,12 @@ Deno.test('should generate credential request options suitable for sending via J challenge: challengeString, allowCredentials: [ { - id: 'MTIzNA', + id: '1234', type: 'public-key', transports: ['usb', 'nfc'], }, { - id: 'NTY3OA', + id: '5678', type: 'public-key', transports: ['internal'], }, @@ -51,8 +49,8 @@ Deno.test('defaults to 60 seconds if no timeout is specified', async () => { const options = await generateAuthenticationOptions({ challenge: challengeBuffer, allowCredentials: [ - { id: isoUint8Array.fromASCIIString('1234'), type: 'public-key' }, - { id: isoUint8Array.fromASCIIString('5678'), type: 'public-key' }, + { id: '1234' }, + { id: '5678' }, ], }); @@ -63,8 +61,8 @@ Deno.test('should set userVerification to "preferred" if not specified', async ( const options = await generateAuthenticationOptions({ challenge: challengeBuffer, allowCredentials: [ - { id: isoUint8Array.fromASCIIString('1234'), type: 'public-key' }, - { id: isoUint8Array.fromASCIIString('5678'), type: 'public-key' }, + { id: '1234' }, + { id: '5678' }, ], }); @@ -94,8 +92,8 @@ Deno.test('should set userVerification if specified', async () => { const options = await generateAuthenticationOptions({ challenge: challengeBuffer, allowCredentials: [ - { id: isoUint8Array.fromASCIIString('1234'), type: 'public-key' }, - { id: isoUint8Array.fromASCIIString('5678'), type: 'public-key' }, + { id: '1234' }, + { id: '5678' }, ], userVerification: 'required', }); @@ -107,8 +105,8 @@ Deno.test('should set extensions if specified', async () => { const options = await generateAuthenticationOptions({ challenge: challengeBuffer, allowCredentials: [ - { id: isoUint8Array.fromASCIIString('1234'), type: 'public-key' }, - { id: isoUint8Array.fromASCIIString('5678'), type: 'public-key' }, + { id: '1234' }, + { id: '5678' }, ], extensions: { appid: 'simplewebauthn' }, }); @@ -117,15 +115,13 @@ Deno.test('should set extensions if specified', async () => { }); Deno.test('should generate a challenge if one is not provided', async () => { - const opts = { + // @ts-ignore 2345 + const options = await generateAuthenticationOptions({ allowCredentials: [ - { id: isoUint8Array.fromASCIIString('1234'), type: 'public-key' }, - { id: isoUint8Array.fromASCIIString('5678'), type: 'public-key' }, + { id: '1234' }, + { id: '5678' }, ], - }; - - // @ts-ignore 2345 - const options = await generateAuthenticationOptions(opts); + }); // Assert basic properties of the challenge assert(options.challenge.length >= 16); diff --git a/packages/server/src/authentication/generateAuthenticationOptions.ts b/packages/server/src/authentication/generateAuthenticationOptions.ts index b1c8166..44ed2b7 100644 --- a/packages/server/src/authentication/generateAuthenticationOptions.ts +++ b/packages/server/src/authentication/generateAuthenticationOptions.ts @@ -1,6 +1,7 @@ import type { AuthenticationExtensionsClientInputs, - PublicKeyCredentialDescriptorFuture, + AuthenticatorTransportFuture, + Base64URLString, PublicKeyCredentialRequestOptionsJSON, UserVerificationRequirement, } from '../deps.ts'; @@ -8,7 +9,10 @@ import { isoBase64URL, isoUint8Array } from '../helpers/iso/index.ts'; import { generateChallenge } from '../helpers/generateChallenge.ts'; export type GenerateAuthenticationOptionsOpts = { - allowCredentials?: PublicKeyCredentialDescriptorFuture[]; + allowCredentials?: { + id: Base64URLString; + transports?: AuthenticatorTransportFuture[]; + }[]; challenge?: string | Uint8Array; timeout?: number; userVerification?: UserVerificationRequirement; @@ -51,10 +55,17 @@ export async function generateAuthenticationOptions( return { challenge: isoBase64URL.fromBuffer(_challenge), - allowCredentials: allowCredentials?.map((cred) => ({ - ...cred, - id: isoBase64URL.fromBuffer(cred.id as Uint8Array), - })), + allowCredentials: allowCredentials?.map((cred) => { + if (!isoBase64URL.isBase64URL(cred.id)) { + throw new Error(`excludeCredential id "${cred.id}" is not a valid base64url string`); + } + + return { + ...cred, + id: isoBase64URL.trimPadding(cred.id), + type: 'public-key', + }; + }), timeout, userVerification, extensions, |