|
// This file is adapted from https://github.com/nextauthjs/next-auth-example/blob/main/pages/api/auth/%5B...nextauth%5D.ts |
|
|
|
import NextAuth, { NextAuthOptions } from "next-auth" |
|
import CredentialsProvider from 'next-auth/providers/credentials' |
|
import jwt from "jsonwebtoken"; |
|
|
|
// Here is where we extract the Knock signing key to use later. |
|
const knockSigningKey = JSON.parse(process.env.KNOCK_SIGNING_KEY as string).key; |
|
|
|
export const authOptions: NextAuthOptions = { |
|
providers: [ |
|
CredentialsProvider({ // Using this provider as an example. |
|
name: "Credentials", |
|
credentials: { |
|
username: { label: "Username", type: "text", placeholder: "jsmith" }, |
|
password: { label: "Password", type: "password" } |
|
}, |
|
async authorize(credentials, req) { |
|
const user = { id: "1", name: "J Smith", email: "[email protected]" } |
|
|
|
if (user) { |
|
return user |
|
} else { |
|
return null |
|
} |
|
} |
|
}), |
|
], |
|
callbacks: { |
|
async session({ session, token, user }) { |
|
// This section is adapted from the Knock docs: https://docs.knock.app/in-app-ui/security-and-authentication#2-sign-the-jwt |
|
// JWT NumericDates specified in seconds: |
|
const currentTime = Math.floor(Date.now() / 1000); |
|
|
|
// Using any because the session type does not support custom properties, but it will pass them through to the client. |
|
(session as any).knockToken = |
|
jwt.sign( |
|
{ |
|
sub: token.sub, // token.sub is the user ID from our provider. You can incorporate the JWT callback, or draw from the user's email, although Knock discourages using email as the user's ID since emails can change but IDs are immutable. |
|
iat: currentTime, |
|
exp: currentTime + 60 * 60, // 1 hour from now |
|
}, |
|
knockSigningKey, |
|
{ |
|
algorithm: "RS256", |
|
}, |
|
); |
|
|
|
// The user ID is passed through here so we can surface it in the component. |
|
(session as any).user.id = token.sub; |
|
|
|
return session; |
|
} |
|
}, |
|
} |
|
|
|
export default NextAuth(authOptions) |