@netizen-experience/auth
v0.1.14
Published
Improved version of DynamoDBAdapter from existing one in next-auth with more complete helper functions, and functions to handle credentials account
Readme
Auth
Adding feature to dynamoDB adapter from next-auth
Table of Contents
Dependency
Add the following peer dependency to your project
npm i \
"@auth/core@^0.40.0" \
"@auth/dynamodb-adapter@^2.8.0" \
"@aws-sdk/client-dynamodb@>=3.758.0" \
"@aws-sdk/client-sesv2@>=3.684.0" \
"@aws-sdk/lib-dynamodb@>=3.758.0" \
"aws-cdk-lib@^2.183.0" \
"constructs@^10.4.2" \
"next@^15.0.0" \
"next-auth@^5.0.0-beta.25" \
"nodemailer@^6.10.0" \
"react@^19.0.0" \
"react-dom@^19.0.0" \
"zod@^3.24.2"Functions
ImprovedDynamoDBAdapter
This library extends the existing DynamoDB adapter from Auth.js (@auth/dynamodb-adapter) to include more helper functions to interact with the DynamoDB table used by Auth.js and to handle and persist credential account.
To instantiate the adapter:
import { DynamoDBDocument } from "@aws-sdk/lib-dynamodb";
import { ImprovedDynamoDBAdapter } from "@netizen-experience/auth-lib";
const document = DynamoDBDocument.from(new DynamoDB());
const adapter = ImprovedDynamoDBAdapter(document, { tableName: "next-auth" });This library added methods that were in the Adapter interface but were not implemented in the original @auth/dynamodb-adapter, as well as new methods to help in handling credentials provider:
getAccount
- Get account by provider account id and provider. If an account is not found, the adapter must return null. (See Auth.js documentation for implementation details.)
updateAccount
Updates attributes of an existing account in the database and returns it. Requires userId, provider, and providerAccountId to identify the account, then updates the other attributes passed in for the account entry. If the account does not exist, returns null.
Parameters
| Parameter | Type |
| --------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| data | Omit<Partial<AdapterAccount>, "userId" | "provider" | "providerAccountId"> & Required<Pick<AdapterAccout, "userId" | "provider" | "providerAccountId">> |
Returns
Promise<AdapterAccount|null>
Example
Say you want to have a field name in AdapterAccount to store the name of the user. You can update the account with the new name like so:
// This would return the updated account object if the account exists.
await adapter.updateAccount({
userId: "<user-id>",
provider: "credentials",
providerAccountId: "<provider-account-id>",
name: "John Doe",
});createUserWithCredentials
Creates a user under Credentials provider, or links a Credentials account to an existing user, and returns the user object. Requires email, password, and whatever other fields you have in your AdapterUser type excluding id and emailVerified that are optional.
Parameters
| Parameter | Type |
| --------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| data | Omit<AdapterUser, "id" | "emailVerified"> & Partial<Pick<AdapterUser, "id" | "emailVerified">> & { email: string; password: string } |
Returns
Promise<AdapterUser|null>
Example
await adapter.createUserWithCredentials({
email: "[email protected]",
password: "password",
name: "John Doe",
image: "https://example.com/john-doe.jpg",
... // other fields
});Credentials Provider
Set up credentials provider to use with Auth.js using the setupCredentialsProvider function.
Parameters
Pass the following fields as an object to the setupCredentialsProvider function:
| Attribute | Type | Description |
| --------- | -------------------------------------------- | ------------------------------------------------------------------------------------------------------------------- |
| adapter | Adapter | The adapter to use with the credentials provider that needs to have both getUserByEmail and getAccount methods. |
| fields | CredentialsFields | The input fields needed for credentials account. |
| schema | Schema extends BaseSchema | The Zod schema to validate the input fields. |
Example
const CredentialsProvider = setupCredentialsProvider({
adapter: ImprovedDynamoDBAdapter(... /* adapter options */),
fields: {
email: { label: "Email", type: "email", placeholder: "[email protected]" },
password: { label: "Password", type: "password" },
... // other fields to create a credential account in your application
},
schema: z.object({
email: z.string().email(),
password: z.string().min(8)
... // other fields schema to validate the input fields
}),
});
const authResult = NextAuth({
providers: [CredentialsProvider, ... /* other providers */],
... // other options
})Nodemailer Provider
Set up nodemailer provider to use with Auth.js using the setupNodemailerProvider function.
Parameters
Pass the following fields as an object to the setupNodemailerProvider function:
| Attribute | Type | Description |
| --------- | ------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------- |
| client | SESv2Client | The SESv2Client instance |
| config | NodemailerUserConfig | The nodemailer provider config |
| mail | MailOptions | The mail templates and other nodemailer's mail options for verification request |
Examples
const NodemailerProvider = setupNodemailerProvider({
client: new SESv2Client(),
config: {
from: "Support <[email protected]>",
secret: process.env.NODEMAILER_SECRET, // secret to encrypt the token
... /* other necessary nodemailer config */
},
mail: {
subject: ({ host }) => `Sign in to ${host}`,
text: ({ url, host }) => `Sign in to ${host}, click this link: ${url}`,
html: ({ url, host, }) => `<p>Sign in to ${host}, click <a href='${url}'>here</a>.</p>`,
},
});
const authResult = NextAuth({
providers: [NodemailerProvider, ... /* other providers */],
... // other options
});Setting up Auth.js
Assuming you have go through the above sections, you can now set up Auth.js with the providers you have set up.
// Say you have set up adapter, CredentialsProvider, and NodemailerProvider as shown above
const { auth, handlers, signIn, signOut } = NextAuth({
providers: [CredentialsProvider, NodemailerProvider, ... /* other providers */],
adapter,
});Types and Interfaces
Adapter
Extended from @auth/core/adapters, with additional methods updateAccount and createUserWithCredentials. See ImprovedDynamoDBAdapter.
AdapterAccount
Extended from @auth/core/adapters, with additional attributes pwHash and salt. These are tailored to be used with the Credentials provider to store hashed passwords and salts.
New attributes:
pwHash:string | undefinedsalt:string | undefined
ClientAdapterUser
Represents a user object on the application client side with optional fields. This type is derived from AdapterUser by making emailVerified and id properties optional. It is used to represent the user in the application where some fields might not be required.
Omit<AdapterUser,"emailVerified"|"id"> &Partial<Pick<AdapterUser,"emailVerified"|"id">>;
CredentialsFields
Represents the fields required for credentials attribute in Credentials provider, but this type enforces email and password to be required, and the rest of fields are optional and can be any of the fields in ClientAdapterUser.
Omit<Record<keyofClientAdapterUser,CredentialInput>,"email"> &Required<Pick<ClientAdapterUser,"email">> & {password:CredentialInput};
BaseClientCredentials
Base type for credentials input type used in the application. This type is used to represent the credentials in the application where email and password are required.
- {
email:string;password:string};
BaseSchema
Base Zod schema for credentials input type used in the application. This type is used to validate the credentials in the application where email and password are required.
z.ZodType<BaseClientCredentials&Record<string,NativeAttributeValue>>;
MailOptions
Represents the object that needs to be passed to setupNodemailerProvider function. It contains the options from nodemailer Mail and the email templates functions to generate verification request email.
Omit<Mail.Options,"to"|"from"|"subject"|"html"|"text"> & {subject?:EmailTemplateFunction;html?:EmailTemplateFunction;text?:EmailTemplateFunction};
EmailTemplateFunction
Represents a function that generates an email template. This function takes an object with url, host, and identifier properties and returns a string. This is the parameter type for subject, html, and text properties in MailOptions. See Auth.js documentation for more details.
- (
params: {url:string;host?:string;identifier?:string}) =>string;
