You're Invited:Meet the Socket Team at BlackHat and DEF CON in Las Vegas, Aug 7-8.RSVP
Socket
Socket
Sign inDemoInstall

@auth/core

Package Overview
Dependencies
7
Maintainers
2
Versions
90
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

Comparing version 0.26.0 to 0.26.1

15

lib/pages/index.js

@@ -8,4 +8,3 @@ import { renderToString } from "preact-render-to-string";

import { UnknownAction } from "../../errors.js";
import { getSimpleWebAuthnBrowserScriptTag } from "../../providers/webauthn.js";
function send({ html, title, status, cookies, theme, headTags }) {
function send({ html, title, status, cookies, theme, headTags, }) {
return {

@@ -62,6 +61,10 @@ cookies,

// render the script in the page.
const webauthnProvider = providers?.find((p) => p.type === "webauthn" && p.enableConditionalUI);
const simpleWebAuthnBrowserScript = webauthnProvider ?
getSimpleWebAuthnBrowserScriptTag(webauthnProvider) :
undefined;
const webauthnProvider = providers?.find((p) => p.type === "webauthn" &&
p.enableConditionalUI &&
!!p.simpleWebAuthnBrowserVersion);
let simpleWebAuthnBrowserScript = "";
if (webauthnProvider) {
const { simpleWebAuthnBrowserVersion } = webauthnProvider;
simpleWebAuthnBrowserScript = `<script src="https://unpkg.com/browse/@simplewebauthn/browser@${simpleWebAuthnBrowserVersion}/dist/bundle/index.umd.min.js" crossorigin="anonymous"></script>`;
}
return send({

@@ -68,0 +71,0 @@ cookies,

9

lib/utils/webauthn-utils.js
import { AdapterError, AuthError, InvalidProvider, MissingAdapter, WebAuthnVerificationError } from "../../errors";
import { webauthnChallenge } from "../actions/callback/oauth/checks";
import { generateAuthenticationOptions, generateRegistrationOptions, verifyAuthenticationResponse, verifyRegistrationResponse } from "@simplewebauthn/server";
import { randomString } from "./web";

@@ -132,3 +131,3 @@ /**

const relayingParty = provider.getRelayingParty(options, request);
verification = await verifyAuthenticationResponse({
verification = await provider.simpleWebAuthn.verifyAuthenticationResponse({
...provider.verifyAuthenticationOptions,

@@ -192,3 +191,3 @@ expectedChallenge,

const relayingParty = provider.getRelayingParty(options, request);
verification = await verifyRegistrationResponse({
verification = await provider.simpleWebAuthn.verifyRegistrationResponse({
...provider.verifyRegistrationOptions,

@@ -247,3 +246,3 @@ expectedChallenge,

// Return the authentication options.
return await generateAuthenticationOptions({
return await provider.simpleWebAuthn.generateAuthenticationOptions({
...provider.authenticationOptions,

@@ -277,3 +276,3 @@ rpID: relayingParty.id,

// Return the registration options.
return await generateRegistrationOptions({
return await provider.simpleWebAuthn.generateRegistrationOptions({
...provider.registrationOptions,

@@ -280,0 +279,0 @@ userID,

{
"name": "@auth/core",
"version": "0.26.0",
"version": "0.26.1",
"description": "Authentication for the Web.",

@@ -73,2 +73,3 @@ "keywords": [

"peerDependencies": {
"@simplewebauthn/browser": "^9.0.1",
"@simplewebauthn/server": "^9.0.1",

@@ -78,2 +79,5 @@ "nodemailer": "^6.8.0"

"peerDependenciesMeta": {
"@simplewebauthn/browser": {
"optional": true
},
"@simplewebauthn/server": {

@@ -80,0 +84,0 @@ "optional": true

@@ -0,4 +1,5 @@

import { generateAuthenticationOptions, generateRegistrationOptions, verifyAuthenticationResponse, verifyRegistrationResponse } from "@simplewebauthn/server";
import type { CommonProviderOptions, CredentialInput } from ".";
import type { GenerateRegistrationOptionsOpts, GenerateAuthenticationOptionsOpts, VerifyAuthenticationResponseOpts, VerifyRegistrationResponseOpts } from "@simplewebauthn/server";
import type { InternalOptions, RequestInternal, SemverString, User } from "../types";
import type { InternalOptions, RequestInternal, SemverString, User } from "../types.js";
export type WebAuthnProviderType = "webauthn";

@@ -99,2 +100,9 @@ export declare const DEFAULT_WEBAUTHN_TIMEOUT: number;

getUserInfo: GetUserInfo;
/** SimpleWebAuthn instance to use for registration and authentication. */
simpleWebAuthn: {
verifyAuthenticationResponse: typeof verifyAuthenticationResponse;
verifyRegistrationResponse: typeof verifyRegistrationResponse;
generateAuthenticationOptions: typeof generateAuthenticationOptions;
generateRegistrationOptions: typeof generateRegistrationOptions;
};
}

@@ -140,9 +148,3 @@ /**

export default function WebAuthn(config: Partial<WebAuthnConfig>): WebAuthnConfig;
/**
* Builds and returns the script tag to load the SimpleWebAuthn browser script.
* @param config Provider config
* @returns The script tag to load the SimpleWebAuthn browser script, or an empty string if the provider has no conditional UI enabled.
*/
export declare function getSimpleWebAuthnBrowserScriptTag(config: WebAuthnConfig): string;
export {};
//# sourceMappingURL=webauthn.d.ts.map

@@ -1,4 +0,5 @@

import { MissingAdapter } from "../errors";
import { generateAuthenticationOptions, generateRegistrationOptions, verifyAuthenticationResponse, verifyRegistrationResponse, } from "@simplewebauthn/server";
import { MissingAdapter } from "../errors.js";
export const DEFAULT_WEBAUTHN_TIMEOUT = 5 * 60 * 1000; // 5 minutes
export const DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION = "v9.0.0";
export const DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION = "v9.0.1";
/**

@@ -47,9 +48,17 @@ * Add WebAuthn login to your page.

enableConditionalUI: true,
authenticationOptions: {
timeout: DEFAULT_WEBAUTHN_TIMEOUT,
simpleWebAuthn: {
generateAuthenticationOptions,
generateRegistrationOptions,
verifyAuthenticationResponse,
verifyRegistrationResponse,
},
registrationOptions: {
timeout: DEFAULT_WEBAUTHN_TIMEOUT,
authenticationOptions: { timeout: DEFAULT_WEBAUTHN_TIMEOUT },
registrationOptions: { timeout: DEFAULT_WEBAUTHN_TIMEOUT },
formFields: {
email: {
label: "Email",
required: true,
autocomplete: "username webauthn",
},
},
formFields: { email: { label: "Email", required: true, autocomplete: "username webauthn" } },
simpleWebAuthnBrowserVersion: DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION,

@@ -86,50 +95,30 @@ getUserInfo,

if (existingUser) {
return {
user: existingUser,
exists: true,
};
return { user: existingUser, exists: true };
}
// If the user does not exist, return a new user info.
return {
user: {
email,
},
exists: false,
};
return { user: { email }, exists: false };
};
/**
* Builds and returns the script tag to load the SimpleWebAuthn browser script.
* @param config Provider config
* @returns The script tag to load the SimpleWebAuthn browser script, or an empty string if the provider has no conditional UI enabled.
*/
export function getSimpleWebAuthnBrowserScriptTag(config) {
const { simpleWebAuthnBrowserVersion, enableConditionalUI } = config;
if (!simpleWebAuthnBrowserVersion || !enableConditionalUI)
return "";
return `<script src="https://unpkg.com/@simplewebauthn/browser@${simpleWebAuthnBrowserVersion}/dist/bundle/index.es5.umd.min.js" crossorigin="anonymous"></script>`;
}
/**
* Retrieves the relaying party information based on the provided options.
* If the relaying party information is not provided, it falls back to using the URL information.
*
* @param options - The options object containing the provider and URL information.
* @returns The relaying party object with the ID, name, and origin.
*/
function getRelayingParty(options) {
function getRelayingParty(
/** The options object containing the provider and URL information. */
options) {
const { provider, url } = options;
const { relayingParty } = provider;
const id = relayingParty && relayingParty.id ?
(Array.isArray(relayingParty.id) ? relayingParty.id[0] : relayingParty.id) :
url.hostname;
const name = relayingParty && relayingParty.name ?
(Array.isArray(relayingParty.name) ? relayingParty.name[0] : relayingParty.name) :
url.host;
const origin = relayingParty && relayingParty.origin ?
(Array.isArray(relayingParty.origin) ? relayingParty.origin[0] : relayingParty.origin) :
url.origin;
const id = Array.isArray(relayingParty?.id)
? relayingParty.id[0]
: relayingParty?.id;
const name = Array.isArray(relayingParty?.name)
? relayingParty.name[0]
: relayingParty?.name;
const origin = Array.isArray(relayingParty?.origin)
? relayingParty.origin[0]
: relayingParty?.origin;
return {
id,
name,
origin,
id: id ?? url.hostname,
name: name ?? url.host,
origin: origin ?? url.origin,
};
}

@@ -17,5 +17,11 @@ import { renderToString } from "preact-render-to-string"

import type { Cookie } from "../utils/cookie.js"
import { getSimpleWebAuthnBrowserScriptTag } from "../../providers/webauthn.js"
function send({ html, title, status, cookies, theme, headTags }: any): ResponseInternal {
function send({
html,
title,
status,
cookies,
theme,
headTags,
}: any): ResponseInternal {
return {

@@ -27,3 +33,5 @@ cookies,

headTags ?? ""
}</head><body class="__next-auth-theme-${theme?.colorScheme ?? "auto"}"><div class="page">${renderToString(html)}</div></body></html>`,
}</head><body class="__next-auth-theme-${
theme?.colorScheme ?? "auto"
}"><div class="page">${renderToString(html)}</div></body></html>`,
}

@@ -92,8 +100,14 @@ }

const webauthnProvider = providers?.find(
(p): p is InternalProvider<"webauthn"> => p.type === "webauthn" && p.enableConditionalUI
(p): p is InternalProvider<"webauthn"> =>
p.type === "webauthn" &&
p.enableConditionalUI &&
!!p.simpleWebAuthnBrowserVersion
)
const simpleWebAuthnBrowserScript = webauthnProvider ?
getSimpleWebAuthnBrowserScriptTag(webauthnProvider) :
undefined
let simpleWebAuthnBrowserScript = ""
if (webauthnProvider) {
const { simpleWebAuthnBrowserVersion } = webauthnProvider
simpleWebAuthnBrowserScript = `<script src="https://unpkg.com/browse/@simplewebauthn/browser@${simpleWebAuthnBrowserVersion}/dist/bundle/index.umd.min.js" crossorigin="anonymous"></script>`
}
return send({

@@ -100,0 +114,0 @@ cookies,

@@ -1,2 +0,2 @@

import type { RelayingParty, WebAuthnProviderType } from "../../providers/webauthn";
import type { WebAuthnProviderType } from "../../providers/webauthn";
import type { Account, Authenticator, Awaited, InternalOptions, RequestInternal, ResponseInternal, User } from "../../types";

@@ -6,3 +6,2 @@ import type { Cookie } from "./cookie";

import { webauthnChallenge } from "../actions/callback/oauth/checks";
import { VerifiedAuthenticationResponse, VerifiedRegistrationResponse, generateAuthenticationOptions, generateRegistrationOptions, verifyAuthenticationResponse, verifyRegistrationResponse } from "@simplewebauthn/server";
import type {

@@ -17,2 +16,3 @@ AuthenticationResponseJSON,

import { randomString } from "./web";
import type { VerifiedAuthenticationResponse, VerifiedRegistrationResponse } from "@simplewebauthn/server";

@@ -203,3 +203,3 @@ export type WebAuthnRegister = "register"

const relayingParty = provider.getRelayingParty(options, request)
verification = await verifyAuthenticationResponse({
verification = await provider.simpleWebAuthn.verifyAuthenticationResponse({
...provider.verifyAuthenticationOptions,

@@ -280,3 +280,3 @@ expectedChallenge,

const relayingParty = provider.getRelayingParty(options, request)
verification = await verifyRegistrationResponse({
verification = await provider.simpleWebAuthn.verifyRegistrationResponse({
...provider.verifyRegistrationOptions,

@@ -343,3 +343,3 @@ expectedChallenge,

// Return the authentication options.
return await generateAuthenticationOptions({
return await provider.simpleWebAuthn.generateAuthenticationOptions({
...provider.authenticationOptions,

@@ -383,3 +383,3 @@ rpID: relayingParty.id,

// Return the registration options.
return await generateRegistrationOptions({
return await provider.simpleWebAuthn.generateRegistrationOptions({
...provider.registrationOptions,

@@ -386,0 +386,0 @@ userID,

@@ -0,6 +1,23 @@

import {
generateAuthenticationOptions,
generateRegistrationOptions,
verifyAuthenticationResponse,
verifyRegistrationResponse,
} from "@simplewebauthn/server"
import { MissingAdapter } from "../errors.js"
import type { CommonProviderOptions, CredentialInput } from "."
import type { GenerateRegistrationOptionsOpts, GenerateAuthenticationOptionsOpts, VerifyAuthenticationResponseOpts, VerifyRegistrationResponseOpts } from "@simplewebauthn/server"
import type { InternalOptions, RequestInternal, SemverString, User } from "../types"
import { MissingAdapter } from "../errors"
import type {
GenerateRegistrationOptionsOpts,
GenerateAuthenticationOptionsOpts,
VerifyAuthenticationResponseOpts,
VerifyRegistrationResponseOpts,
} from "@simplewebauthn/server"
import type {
InternalOptions,
RequestInternal,
SemverString,
User,
} from "../types.js"

@@ -10,3 +27,3 @@ export type WebAuthnProviderType = "webauthn"

export const DEFAULT_WEBAUTHN_TIMEOUT = 5 * 60 * 1000 // 5 minutes
export const DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION: SemverString = "v9.0.0"
export const DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION: SemverString = "v9.0.1"

@@ -33,17 +50,36 @@ export type RelayingParty = {

options: InternalOptions<WebAuthnProviderType>,
request: RequestInternal,
) => Promise<{
user: User
exists: true
} | {
user: Omit<User, "id">
exists: false
} | null>
request: RequestInternal
) => Promise<
| { user: User; exists: true }
| { user: Omit<User, "id">; exists: false }
| null
>
type ConfigurableAuthenticationOptions = Omit<
GenerateAuthenticationOptionsOpts,
"rpID" | "allowCredentials" | "challenge"
>
type ConfigurableRegistrationOptions = Omit<
GenerateRegistrationOptionsOpts,
| "rpName"
| "rpID"
| "userID"
| "userName"
| "challenge"
| "userDisplayName"
| "excludeCredentials"
>
type ConfigurableVerifyAuthenticationOptions = Omit<
VerifyAuthenticationResponseOpts,
| "expectedChallenge"
| "expectedOrigin"
| "expectedRPID"
| "authenticator"
| "response"
>
type ConfigurableVerifyRegistrationOptions = Omit<
VerifyRegistrationResponseOpts,
"expectedChallenge" | "expectedOrigin" | "expectedRPID" | "response"
>
type ConfigurableAuthenticationOptions = Omit<GenerateAuthenticationOptionsOpts, "rpID" | "allowCredentials" | "challenge">
type ConfigurableRegistrationOptions = Omit<GenerateRegistrationOptionsOpts, "rpName" | "rpID" | "userID" | "userName" | "challenge" | "userDisplayName" | "excludeCredentials">
type ConfigurableVerifyAuthenticationOptions = Omit<VerifyAuthenticationResponseOpts, "expectedChallenge" | "expectedOrigin" | "expectedRPID" | "authenticator" | "response">
type ConfigurableVerifyRegistrationOptions = Omit<VerifyRegistrationResponseOpts, "expectedChallenge" | "expectedOrigin" | "expectedRPID" | "response">
export interface WebAuthnConfig extends CommonProviderOptions {

@@ -53,3 +89,3 @@ type: WebAuthnProviderType

* Relaying party (RP) configuration
*
*
* If not provided, the request URL will be used.

@@ -61,6 +97,9 @@ **/

*/
getRelayingParty: (options: InternalOptions<WebAuthnProviderType>, request: RequestInternal) => RelayingParty
getRelayingParty: (
options: InternalOptions<WebAuthnProviderType>,
request: RequestInternal
) => RelayingParty
/**
* Enable conditional UI.
*
*
* NOTE: Only one provider can have this option enabled at a time. Defaults to `true`.

@@ -71,3 +110,3 @@ */

* Version of SimpleWebAuthn browser script to load in the sign in page.
*
*
* This is only loaded if the provider has conditional UI enabled. If set to false, it won't load any script.

@@ -79,3 +118,3 @@ * Defaults to `v9.0.0`.

* These are not validated or enforced beyond the default Auth.js authentication page.
*
*
* By default it displays an email field.

@@ -102,3 +141,3 @@ */

* Function that returns the user info that the authenticator will use during registration and authentication.
*
*
* - It accepts the provider options, the request object, and returns the user info.

@@ -108,5 +147,5 @@ * - If the request contains an existing user's data (e.g. email address), the function must return the existing user and `exists` must be `true`.

* - If the request does not contain enough information to create a new user, the function must return `null`.
*
*
* It should not have any side effects (i.e. it shall not modify the database).
*
*
* During passkey creation:

@@ -116,6 +155,13 @@ * - The passkey's user ID will be a random string.

* - The passkey's user display name will be user.name, if present, or user.email
*
*
* By default, it looks for and uses the "email" request parameter to look up the user in the database.
*/
getUserInfo: GetUserInfo
/** SimpleWebAuthn instance to use for registration and authentication. */
simpleWebAuthn: {
verifyAuthenticationResponse: typeof verifyAuthenticationResponse
verifyRegistrationResponse: typeof verifyRegistrationResponse
generateAuthenticationOptions: typeof generateAuthenticationOptions
generateRegistrationOptions: typeof generateRegistrationOptions
}
}

@@ -125,5 +171,5 @@

* Add WebAuthn login to your page.
*
*
* ### Setup
*
*
* #### Configuration

@@ -162,3 +208,5 @@ * ```ts

*/
export default function WebAuthn(config: Partial<WebAuthnConfig>): WebAuthnConfig {
export default function WebAuthn(
config: Partial<WebAuthnConfig>
): WebAuthnConfig {
return {

@@ -168,9 +216,17 @@ id: "webauthn",

enableConditionalUI: true,
authenticationOptions: {
timeout: DEFAULT_WEBAUTHN_TIMEOUT,
simpleWebAuthn: {
generateAuthenticationOptions,
generateRegistrationOptions,
verifyAuthenticationResponse,
verifyRegistrationResponse,
},
registrationOptions: {
timeout: DEFAULT_WEBAUTHN_TIMEOUT,
authenticationOptions: { timeout: DEFAULT_WEBAUTHN_TIMEOUT },
registrationOptions: { timeout: DEFAULT_WEBAUTHN_TIMEOUT },
formFields: {
email: {
label: "Email",
required: true,
autocomplete: "username webauthn",
},
},
formFields: { email: { label: "Email", required: true, autocomplete: "username webauthn" } },
simpleWebAuthnBrowserVersion: DEFAULT_SIMPLEWEBAUTHN_BROWSER_VERSION,

@@ -186,6 +242,6 @@ getUserInfo,

* Retrieves user information for the WebAuthn provider.
*
*
* It looks for the "email" query parameter and uses it to look up the user in the database.
* It also accepts a "name" query parameter to set the user's display name.
*
*
* @param options - The internaloptions object.

@@ -213,56 +269,36 @@ * @param request - The request object containing the query parameters.

if (existingUser) {
return {
user: existingUser,
exists: true,
}
return { user: existingUser, exists: true }
}
// If the user does not exist, return a new user info.
return {
user: {
email,
},
exists: false,
}
return { user: { email }, exists: false }
}
/**
* Builds and returns the script tag to load the SimpleWebAuthn browser script.
* @param config Provider config
* @returns The script tag to load the SimpleWebAuthn browser script, or an empty string if the provider has no conditional UI enabled.
*/
export function getSimpleWebAuthnBrowserScriptTag(config: WebAuthnConfig) {
const { simpleWebAuthnBrowserVersion, enableConditionalUI } = config
if (!simpleWebAuthnBrowserVersion || !enableConditionalUI)
return ""
return `<script src="https://unpkg.com/@simplewebauthn/browser@${simpleWebAuthnBrowserVersion}/dist/bundle/index.es5.umd.min.js" crossorigin="anonymous"></script>`
}
/**
* Retrieves the relaying party information based on the provided options.
* If the relaying party information is not provided, it falls back to using the URL information.
*
* @param options - The options object containing the provider and URL information.
* @returns The relaying party object with the ID, name, and origin.
*/
function getRelayingParty(options: InternalOptions<WebAuthnProviderType>): RelayingParty {
function getRelayingParty(
/** The options object containing the provider and URL information. */
options: InternalOptions<WebAuthnProviderType>
): RelayingParty {
const { provider, url } = options
const { relayingParty } = provider
const id = relayingParty && relayingParty.id ?
(Array.isArray(relayingParty.id) ? relayingParty.id[0] : relayingParty.id) :
url.hostname
const name = relayingParty && relayingParty.name ?
(Array.isArray(relayingParty.name) ? relayingParty.name[0] : relayingParty.name) :
url.host
const origin = relayingParty && relayingParty.origin ?
(Array.isArray(relayingParty.origin) ? relayingParty.origin[0] : relayingParty.origin) :
url.origin
const id = Array.isArray(relayingParty?.id)
? relayingParty.id[0]
: relayingParty?.id
const name = Array.isArray(relayingParty?.name)
? relayingParty.name[0]
: relayingParty?.name
const origin = Array.isArray(relayingParty?.origin)
? relayingParty.origin[0]
: relayingParty?.origin
return {
id,
name,
origin,
id: id ?? url.hostname,
name: name ?? url.host,
origin: origin ?? url.origin,
}
}

@@ -76,3 +76,3 @@ /**

} from "./providers/index.js"
import {
import type {
WebAuthnConfig,

@@ -79,0 +79,0 @@ WebAuthnProviderType,

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc