From 96f51eca56bf799e720716fb4bd2968c89f3712b Mon Sep 17 00:00:00 2001 From: Andrew Prifer Date: Thu, 5 Oct 2023 14:14:13 +1100 Subject: [PATCH] Replace Auth0 with NextAuth --- packages/app/.env.example | 5 +- packages/app/package.json | 3 +- .../migration.sql | 74 ++++++ packages/app/prisma/schema.prisma | 50 +++- packages/app/src/pages/_app.tsx | 14 +- packages/app/src/pages/api/auth/[...auth0].ts | 4 - .../app/src/pages/api/auth/[...nextauth].ts | 4 + packages/app/src/pages/api/studio-auth.ts | 11 +- packages/app/src/pages/index.tsx | 13 +- packages/app/src/pages/projects/index.tsx | 2 +- packages/app/src/utils/authUtils.ts | 77 +++--- .../app/src/utils/withPageAuthRequired.tsx | 27 +++ yarn.lock | 226 +++++++++++------- 13 files changed, 351 insertions(+), 159 deletions(-) create mode 100644 packages/app/prisma/migrations/20231005010012_replace_auth0_with_next_auth/migration.sql delete mode 100644 packages/app/src/pages/api/auth/[...auth0].ts create mode 100644 packages/app/src/pages/api/auth/[...nextauth].ts create mode 100644 packages/app/src/utils/withPageAuthRequired.tsx diff --git a/packages/app/.env.example b/packages/app/.env.example index a378c767b..5d879ab09 100644 --- a/packages/app/.env.example +++ b/packages/app/.env.example @@ -17,4 +17,7 @@ AUTH0_CLIENT_ID='client-id' AUTH0_CLIENT_SECRET='client-secret' # these are a public/private keypair. you can generate them via `$ yarn run cli dev generate-keypair` STUDIO_AUTH_JWT_PRIVATE_KEY=-----BEGIN PRIVATE KEY-----MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCSl57bV4RJ3wDj4mDOi2UVM1Ga5+aqLnEkKGA81wx2GCdpJABFW+MC+MQ6H6Qbu/R3zLLx2KwT9RFKnfEPgQoif7tqdZWQnnS3LM3Q+0e0jsV6kKVlo6IIGDSZ2yS1LOCawbfyR6ZmWVbUlPEyz8zJF6i55rw62ekf0R9+oi6LzSzCmYmwcfS386BViC1JLA4Hks8OMQGtnoT7Vccs8gRzQUeauupfxqF3/eTPpdLPksMi6OozW5IfIpD4ppeA+eZ/EaQy1ANrzVzSQGqJTVu5H+ImMifQHlgNs5hVDhYtcfqB+sBlrI7v+3JgkX/UGGv0HirJqQJfl1I1Zhvuu+4zAgMBAAECggEAFaCjAk9uKAvrsLNkfvSX7EHPB2CxamhBrwj58d/0abP0lJGILLN60aRsJvsmFiVr0wTzXbUO5j7g1zZoK1ZpbV+VAgbpExYduCy3DN8V3DC4N/YBQPacYD9Z+10WlFhTpuFvxyIFDdKeeeyjjVCVMRH5hbviB3jA6T3MPL2myl84v164bXGXt7lO542IJ02iupcOLr0M4Qwty8OI8AUNz8Nes8DaIfiWPs3mzhpP7cvzaeHh47kpxZEnwkla2N9VqMi/mFgJkbbi6uYFQQVHTY4PZ0uddrU9MLBh3akxelpXtHyPcAa50god/JKmOLGHOQ8A4plYQ6lP+HtVVkZTGQKBgQDL/Kpxch7G6rklhH9AS7LEIoyg5FwWFJZ6O+a9obBQemHQiVUBan7+CqQGCUz/G460yaWTlKExi7s4o/kwNyyDc4YaxzpZ1eRqQlNpViQzkzbL9BakoNyzfWO0EvpOfCx5UITjfr05iRBFPWomt8fqzbUBQq7TaPBnj3pbMuNLxwKBgQC3+H3OxGaU8foZXFeKttclgpc5UL7ttpqeilcBMHFkNCYQtQHiooxx2mB5IcRLMCqt8+CPolPSODHNGzh69EdgPEb6vJnnLRq7mlvvxv2fAUHxRzwwzt0kJ73i4VS/10vbgjTP/hjumbp8T1NvyrHH5+TjRP35IwmhVywRmlzSNQKBgQCwSD4TpAes55PxNDu0GLb4gNL/B9n8yvXv1GxnXJ++LMTzLntjqeDtMczl2ovLusjsu4Z3r25OHu9A15O1czjosKEn6xwmHo4ytfbXhTXrzEECqIIY61tPUgEj0XK2+OCGRmtRHmnwmt6Qt65Qn2oJJJRT7oie8oUvOfMHdUawaQKBgBs5OFS6l3t++0V5drLeL6QrWPlwS3Cdzu+bBRj19DGhzeg3ANpqt2G5sQD70DJYJFiteBOJL+Ix0pzJZGg9cbp58P71ncip0gTk6KnoxmsbIojzw6JtWigZgW3rbkEdOOp4sBv/O+1C7meqzWwDkJ9GX4aKFRMi7i/j2G+aahXpAoGBAJlX1gVeE1j1D5LDOIKr56kAK4rsHYlleqYNs1iNnQy2rxA+rn0JWLuWRIn9Jvgl1RzPa5UY5CXMg5NlN+U6X2DFtGqpimBIay5Do5c5dqwpCpcckGiwW6mQ+uvbUcQDtko07t0CVtFlsv0WsckRLFf5qyNccdLZ5apQ3RzRYUrd-----END PRIVATE KEY----- -STUDIO_AUTH_JWT_PUBLIC_KEY=-----BEGIN PUBLIC KEY-----MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAkpee21eESd8A4+JgzotlFTNRmufmqi5xJChgPNcMdhgnaSQARVvjAvjEOh+kG7v0d8yy8disE/URSp3xD4EKIn+7anWVkJ50tyzN0PtHtI7FepClZaOiCBg0mdsktSzgmsG38kemZllW1JTxMs/MyReouea8OtnpH9EffqIui80swpmJsHH0t/OgVYgtSSwOB5LPDjEBrZ6E+1XHLPIEc0FHmrrqX8ahd/3kz6XSz5LDIujqM1uSHyKQ+KaXgPnmfxGkMtQDa81c0kBqiU1buR/iJjIn0B5YDbOYVQ4WLXH6gfrAZayO7/tyYJF/1Bhr9B4qyakCX5dSNWYb7rvuMwIDAQAB-----END PUBLIC KEY----- \ No newline at end of file +STUDIO_AUTH_JWT_PUBLIC_KEY=-----BEGIN PUBLIC KEY-----MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAkpee21eESd8A4+JgzotlFTNRmufmqi5xJChgPNcMdhgnaSQARVvjAvjEOh+kG7v0d8yy8disE/URSp3xD4EKIn+7anWVkJ50tyzN0PtHtI7FepClZaOiCBg0mdsktSzgmsG38kemZllW1JTxMs/MyReouea8OtnpH9EffqIui80swpmJsHH0t/OgVYgtSSwOB5LPDjEBrZ6E+1XHLPIEc0FHmrrqX8ahd/3kz6XSz5LDIujqM1uSHyKQ+KaXgPnmfxGkMtQDa81c0kBqiU1buR/iJjIn0B5YDbOYVQ4WLXH6gfrAZayO7/tyYJF/1Bhr9B4qyakCX5dSNWYb7rvuMwIDAQAB-----END PUBLIC KEY----- + +# generate via openssl rand -base64 32 +NEXTAUTH_SECRET='secret' \ No newline at end of file diff --git a/packages/app/package.json b/packages/app/package.json index 3cadb22e3..d60973730 100644 --- a/packages/app/package.json +++ b/packages/app/package.json @@ -13,7 +13,7 @@ "seed": "tsx prisma/seed.ts" }, "dependencies": { - "@auth0/nextjs-auth0": "^3.1.0", + "@auth/prisma-adapter": "^1.0.3", "@prisma/client": "^4.12.0", "@tanstack/react-query": "^4.32.6", "@trpc/client": "^10.38.0", @@ -33,6 +33,7 @@ "jose": "^4.14.4", "nanoid": "^3.3.1", "next": "13.4.13", + "next-auth": "^4.23.2", "npm-run-all": "^4.1.5", "pg": "^8.11.2", "prisma": "^4.12.0", diff --git a/packages/app/prisma/migrations/20231005010012_replace_auth0_with_next_auth/migration.sql b/packages/app/prisma/migrations/20231005010012_replace_auth0_with_next_auth/migration.sql new file mode 100644 index 000000000..98468cef8 --- /dev/null +++ b/packages/app/prisma/migrations/20231005010012_replace_auth0_with_next_auth/migration.sql @@ -0,0 +1,74 @@ +/* + Warnings: + + - You are about to drop the column `auth0Data` on the `User` table. All the data in the column will be lost. + - You are about to drop the column `auth0Sid` on the `User` table. All the data in the column will be lost. + - A unique constraint covering the columns `[email]` on the table `User` will be added. If there are existing duplicate values, this will fail. + +*/ +-- DropIndex +DROP INDEX "User_auth0Sid_key"; + +-- AlterTable +ALTER TABLE "User" DROP COLUMN "auth0Data", +DROP COLUMN "auth0Sid", +ADD COLUMN "emailVerified" TIMESTAMP(3), +ADD COLUMN "image" TEXT, +ADD COLUMN "name" TEXT, +ALTER COLUMN "email" DROP NOT NULL; + +-- CreateTable +CREATE TABLE "Account" ( + "id" TEXT NOT NULL, + "userId" TEXT NOT NULL, + "type" TEXT NOT NULL, + "provider" TEXT NOT NULL, + "providerAccountId" TEXT NOT NULL, + "refresh_token" TEXT, + "access_token" TEXT, + "expires_at" INTEGER, + "token_type" TEXT, + "scope" TEXT, + "id_token" TEXT, + "session_state" TEXT, + + CONSTRAINT "Account_pkey" PRIMARY KEY ("id") +); + +-- CreateTable +CREATE TABLE "Session" ( + "id" TEXT NOT NULL, + "sessionToken" TEXT NOT NULL, + "userId" TEXT NOT NULL, + "expires" TIMESTAMP(3) NOT NULL, + + CONSTRAINT "Session_pkey" PRIMARY KEY ("id") +); + +-- CreateTable +CREATE TABLE "VerificationToken" ( + "identifier" TEXT NOT NULL, + "token" TEXT NOT NULL, + "expires" TIMESTAMP(3) NOT NULL +); + +-- CreateIndex +CREATE UNIQUE INDEX "Account_provider_providerAccountId_key" ON "Account"("provider", "providerAccountId"); + +-- CreateIndex +CREATE UNIQUE INDEX "Session_sessionToken_key" ON "Session"("sessionToken"); + +-- CreateIndex +CREATE UNIQUE INDEX "VerificationToken_token_key" ON "VerificationToken"("token"); + +-- CreateIndex +CREATE UNIQUE INDEX "VerificationToken_identifier_token_key" ON "VerificationToken"("identifier", "token"); + +-- CreateIndex +CREATE UNIQUE INDEX "User_email_key" ON "User"("email"); + +-- AddForeignKey +ALTER TABLE "Account" ADD CONSTRAINT "Account_userId_fkey" FOREIGN KEY ("userId") REFERENCES "User"("id") ON DELETE CASCADE ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "Session" ADD CONSTRAINT "Session_userId_fkey" FOREIGN KEY ("userId") REFERENCES "User"("id") ON DELETE CASCADE ON UPDATE CASCADE; diff --git a/packages/app/prisma/schema.prisma b/packages/app/prisma/schema.prisma index 805b01335..eaf8d5508 100644 --- a/packages/app/prisma/schema.prisma +++ b/packages/app/prisma/schema.prisma @@ -11,17 +11,55 @@ datasource db { url = env("DATABASE_URL") } +model Account { + id String @id @default(cuid()) + userId String + type String + provider String + providerAccountId String + refresh_token String? @db.Text + access_token String? @db.Text + expires_at Int? + token_type String? + scope String? + id_token String? @db.Text + session_state String? + + user User @relation(fields: [userId], references: [id], onDelete: Cascade) + + @@unique([provider, providerAccountId]) +} + model User { - id String @id - auth0Sid String @unique - email String - projects Project[] - libSessions LibSession[] - auth0Data Json + projects Project[] + libSessions LibSession[] + id String @id @default(cuid()) + name String? + email String? @unique + emailVerified DateTime? + image String? + accounts Account[] + sessions Session[] @@index([email], name: "email") } +model Session { + id String @id @default(cuid()) + sessionToken String @unique + userId String + expires DateTime + user User @relation(fields: [userId], references: [id], onDelete: Cascade) +} + +model VerificationToken { + identifier String + token String @unique + expires DateTime + + @@unique([identifier, token]) +} + model Project { id String @id name String? diff --git a/packages/app/src/pages/_app.tsx b/packages/app/src/pages/_app.tsx index 594f34895..5f95d0d10 100644 --- a/packages/app/src/pages/_app.tsx +++ b/packages/app/src/pages/_app.tsx @@ -1,16 +1,14 @@ import React from 'react' -import {UserProvider} from '@auth0/nextjs-auth0/client' +import {SessionProvider} from 'next-auth/react' +import type {AppProps} from 'next/app' export default function App({ Component, - pageProps, -}: { - Component: React.ComponentType - pageProps: any -}) { + pageProps: {session, ...pageProps}, +}: AppProps) { return ( - + - + ) } diff --git a/packages/app/src/pages/api/auth/[...auth0].ts b/packages/app/src/pages/api/auth/[...auth0].ts deleted file mode 100644 index 7d04dc529..000000000 --- a/packages/app/src/pages/api/auth/[...auth0].ts +++ /dev/null @@ -1,4 +0,0 @@ -// pages/api/auth/[...auth0].js -import {handleAuth} from '@auth0/nextjs-auth0' - -export default handleAuth() diff --git a/packages/app/src/pages/api/auth/[...nextauth].ts b/packages/app/src/pages/api/auth/[...nextauth].ts new file mode 100644 index 000000000..e345bf729 --- /dev/null +++ b/packages/app/src/pages/api/auth/[...nextauth].ts @@ -0,0 +1,4 @@ +import NextAuth from 'next-auth' +import {nextAuthConfig} from 'src/utils/authUtils' + +export default NextAuth(nextAuthConfig) diff --git a/packages/app/src/pages/api/studio-auth.ts b/packages/app/src/pages/api/studio-auth.ts index 73854b76b..935f274e8 100644 --- a/packages/app/src/pages/api/studio-auth.ts +++ b/packages/app/src/pages/api/studio-auth.ts @@ -1,8 +1,7 @@ import type {NextApiRequest, NextApiResponse} from 'next' import prisma from 'src/prisma' -import {getSession} from '@auth0/nextjs-auth0' -import {ensureUserFromAuth0Session, studioAuth} from 'src/utils/authUtils' +import {getAppSession, studioAuth} from 'src/utils/authUtils' import {userCodeLength} from 'src/trpc/routes/studioAuthRouter' export default async function libAuth( @@ -35,9 +34,11 @@ export default async function libAuth( return } - const session = await getSession(req, res) + const session = await getAppSession(req, res) + + // if no session, redirect to login if (!session || !session.user) { - res.redirect('/api/auth/login?returnTo=' + encodeURIComponent(req.url!)) + res.redirect(`/api/auth/signin?callbackUrl=${encodeURIComponent(req.url!)}`) return } @@ -72,7 +73,7 @@ export default async function libAuth( return } - const user = await ensureUserFromAuth0Session(req, res) + const user = session.user const {refreshToken, accessToken} = await studioAuth.createSession(user) diff --git a/packages/app/src/pages/index.tsx b/packages/app/src/pages/index.tsx index 252d33f21..c280e6e0c 100644 --- a/packages/app/src/pages/index.tsx +++ b/packages/app/src/pages/index.tsx @@ -1,5 +1,6 @@ import React from 'react' -import {useUser} from '@auth0/nextjs-auth0/client' +import {useSession, signIn, signOut} from 'next-auth/react' + import Link from 'next/link' export default function HomePage() { @@ -12,13 +13,13 @@ export default function HomePage() { } const Profile: React.FC<{}> = () => { - const {user, error, isLoading} = useUser() + const {data: session, status} = useSession() + const user = session?.user - if (isLoading) return
Loading...
- if (error) return
{error.message}
+ if (status === 'loading') return
Loading...
if (!user) { - return log in + return } return ( @@ -27,7 +28,7 @@ const Profile: React.FC<{}> = () => {

{user.name}

{user.email}

Projects
- log out + ) } diff --git a/packages/app/src/pages/projects/index.tsx b/packages/app/src/pages/projects/index.tsx index 37f61dc17..08aa79b85 100644 --- a/packages/app/src/pages/projects/index.tsx +++ b/packages/app/src/pages/projects/index.tsx @@ -1,6 +1,6 @@ -import {withPageAuthRequired} from '@auth0/nextjs-auth0/client' import React, {useState} from 'react' import useApi from '../../useApi' +import {withPageAuthRequired} from 'src/utils/withPageAuthRequired' const ProjectsPage: React.FC<{}> = withPageAuthRequired(({}) => { const {response, error, isLoading} = useApi('/api/projects') diff --git a/packages/app/src/utils/authUtils.ts b/packages/app/src/utils/authUtils.ts index 56936984d..b6698c17c 100644 --- a/packages/app/src/utils/authUtils.ts +++ b/packages/app/src/utils/authUtils.ts @@ -1,48 +1,53 @@ -import type {NextApiRequest, NextApiResponse} from 'next' +import type { + GetServerSidePropsContext, + NextApiRequest, + NextApiResponse, +} from 'next' import type {User} from '../../prisma/client-generated' import prisma from '../prisma' -import {getSession} from '@auth0/nextjs-auth0' import {v4} from 'uuid' import * as jose from 'jose' import type {$IntentionalAny} from 'src/types' import {TRPCError} from '@trpc/server' import {z} from 'zod' - -/** - * Since Auth0 users are not stored in our database, we need to create a user in our database - * whenever we encounter a valid Auth0 session. If the user already exists, we return it. - * - * If the session is not valid, we throw an error. - */ -export async function ensureUserFromAuth0Session( - req: NextApiRequest, - res: NextApiResponse, -): Promise { - const session = await getSession(req, res) - if (!session || !session.user) { - throw new Error(`User is not authenticated`) +import type {AuthOptions} from 'next-auth' +import {getServerSession} from 'next-auth' +import GithubProvider from 'next-auth/providers/github' +import {PrismaAdapter} from '@auth/prisma-adapter' +import type {Adapter} from 'next-auth/adapters' + +// Extend NextAuth Session type to include all fields from the User model +declare module 'next-auth' { + interface Session { + user: User } +} - const user = await prisma.user.findUnique({ - where: { - auth0Sid: session.user.sid, +export const nextAuthConfig = { + // Why type assertion: https://github.com/nextauthjs/next-auth/issues/6106#issuecomment-1582582312 + adapter: PrismaAdapter(prisma) as Adapter, + providers: [ + GithubProvider({ + clientId: process.env.GITHUB_ID!, + clientSecret: process.env.GITHUB_SECRET!, + }), + ], + callbacks: { + session({session, token, user}) { + session.user = {...session.user, ...user} + return session }, - }) - - if (!user) { - const userId = v4() + v4() - const user = await prisma.user.create({ - data: { - auth0Sid: session.user.sid, - email: session.user.email, - auth0Data: session.user, - id: userId, - }, - }) - return user - } - - return user + }, +} satisfies AuthOptions + +// Use it in server contexts +export function getAppSession( + ...args: + | [GetServerSidePropsContext['req'], GetServerSidePropsContext['res']] + | [NextApiRequest, NextApiResponse] + | [] +) { + return getServerSession(...args, nextAuthConfig) } export type AccessTokenPayload = { @@ -63,7 +68,7 @@ export namespace studioAuth { const privateKey = await privateKeyPromise const payload: AccessTokenPayload = { userId: user.id, - email: user.email, + email: user.email ?? '', } const jwt = await new jose.SignJWT(payload) .setProtectedHeader({alg: 'RS256'}) diff --git a/packages/app/src/utils/withPageAuthRequired.tsx b/packages/app/src/utils/withPageAuthRequired.tsx new file mode 100644 index 000000000..060dc7c3e --- /dev/null +++ b/packages/app/src/utils/withPageAuthRequired.tsx @@ -0,0 +1,27 @@ +import type {ComponentType} from 'react' +import {useEffect} from 'react' +import {useSession} from 'next-auth/react' + +export const withPageAuthRequired = (Component: ComponentType) => { + return function WithPageAuthRequired(props: any): JSX.Element { + const {data: session, status} = useSession() + + useEffect(() => { + if (session?.user || status === 'loading') return + let returnToPath: string + + const currentLocation = window.location.toString() + returnToPath = + currentLocation.replace(new URL(currentLocation).origin, '') || '/' + + window.location.assign( + `/api/auth/signin?callbackUrl=${encodeURIComponent(returnToPath)}`, + ) + }, [session, status]) + + if (session?.user) + return + + return
Redirecting...
+ } +} diff --git a/yarn.lock b/yarn.lock index 6aee7f885..307c89bfc 100644 --- a/yarn.lock +++ b/yarn.lock @@ -63,22 +63,33 @@ __metadata: languageName: node linkType: hard -"@auth0/nextjs-auth0@npm:^3.1.0": - version: 3.1.0 - resolution: "@auth0/nextjs-auth0@npm:3.1.0" +"@auth/core@npm:0.16.1": + version: 0.16.1 + resolution: "@auth/core@npm:0.16.1" dependencies: - "@panva/hkdf": ^1.0.2 - cookie: ^0.5.0 - debug: ^4.3.4 - joi: ^17.6.0 - jose: ^4.9.2 - oauth4webapi: ^2.3.0 - openid-client: ^5.2.1 - tslib: ^2.4.0 - url-join: ^4.0.1 + "@panva/hkdf": ^1.0.4 + cookie: 0.5.0 + jose: ^4.11.1 + oauth4webapi: ^2.0.6 + preact: 10.11.3 + preact-render-to-string: 5.2.3 peerDependencies: - next: ">=10" - checksum: e55409d69c49185737f69856b641d5df073099421e4eb61bbbbf0fafa78fe5a50a8376c90edc6ae1993a38468f320513708704a7f98748b4847bfe9556816e25 + nodemailer: ^6.8.0 + peerDependenciesMeta: + nodemailer: + optional: true + checksum: 1bb938fcafb921b511f47c966a94f86de70010be77a196d0db55c7af59c483b81628e29db6b6c6deaa711c7afeae77a56da2e9c640b95a85d959acbdbe7dbb8f + languageName: node + linkType: hard + +"@auth/prisma-adapter@npm:^1.0.3": + version: 1.0.3 + resolution: "@auth/prisma-adapter@npm:1.0.3" + dependencies: + "@auth/core": 0.16.1 + peerDependencies: + "@prisma/client": ">=2.26.0 || >=3 || >=4 || >=5" + checksum: a7629062752b1fc25dfef30721a93660c811739372056ffc526a6e5a040b83680a57f7678843351dde9c016b7066f750141381181b9fad728f71a5fd32c83746 languageName: node linkType: hard @@ -4641,6 +4652,15 @@ __metadata: languageName: node linkType: hard +"@babel/runtime@npm:^7.20.13": + version: 7.23.1 + resolution: "@babel/runtime@npm:7.23.1" + dependencies: + regenerator-runtime: ^0.14.0 + checksum: 0cd0d43e6e7dc7f9152fda8c8312b08321cda2f56ef53d6c22ebdd773abdc6f5d0a69008de90aa41908d00e2c1facb24715ff121274e689305c858355ff02c70 + languageName: node + linkType: hard + "@babel/runtime@npm:^7.20.7": version: 7.22.10 resolution: "@babel/runtime@npm:7.22.10" @@ -6126,13 +6146,6 @@ __metadata: languageName: node linkType: hard -"@hapi/hoek@npm:^9.0.0": - version: 9.3.0 - resolution: "@hapi/hoek@npm:9.3.0" - checksum: 4771c7a776242c3c022b168046af4e324d116a9d2e1d60631ee64f474c6e38d1bb07092d898bf95c7bc5d334c5582798a1456321b2e53ca817d4e7c88bc25b43 - languageName: node - linkType: hard - "@hapi/joi@npm:^15.1.0": version: 15.1.1 resolution: "@hapi/joi@npm:15.1.1" @@ -6154,15 +6167,6 @@ __metadata: languageName: node linkType: hard -"@hapi/topo@npm:^5.0.0": - version: 5.1.0 - resolution: "@hapi/topo@npm:5.1.0" - dependencies: - "@hapi/hoek": ^9.0.0 - checksum: 604dfd5dde76d5c334bd03f9001fce69c7ce529883acf92da96f4fe7e51221bf5e5110e964caca287a6a616ba027c071748ab636ff178ad750547fba611d6014 - languageName: node - linkType: hard - "@humanwhocodes/config-array@npm:^0.11.10": version: 0.11.10 resolution: "@humanwhocodes/config-array@npm:0.11.10" @@ -7350,6 +7354,13 @@ __metadata: languageName: node linkType: hard +"@panva/hkdf@npm:^1.0.4": + version: 1.1.1 + resolution: "@panva/hkdf@npm:1.1.1" + checksum: f0dd12903751d8792420353f809ed3c7de860cf506399759fff5f59f7acfef8a77e2b64012898cee7e5b047708fa0bd91dff5ef55a502bf8ea11aad9842160da + languageName: node + linkType: hard + "@parcel/fs@npm:^1.11.0": version: 1.11.0 resolution: "@parcel/fs@npm:1.11.0" @@ -7965,29 +7976,6 @@ __metadata: languageName: node linkType: hard -"@sideway/address@npm:^4.1.3": - version: 4.1.4 - resolution: "@sideway/address@npm:4.1.4" - dependencies: - "@hapi/hoek": ^9.0.0 - checksum: b9fca2a93ac2c975ba12e0a6d97853832fb1f4fb02393015e012b47fa916a75ca95102d77214b2a29a2784740df2407951af8c5dde054824c65577fd293c4cdb - languageName: node - linkType: hard - -"@sideway/formula@npm:^3.0.1": - version: 3.0.1 - resolution: "@sideway/formula@npm:3.0.1" - checksum: e4beeebc9dbe2ff4ef0def15cec0165e00d1612e3d7cea0bc9ce5175c3263fc2c818b679bd558957f49400ee7be9d4e5ac90487e1625b4932e15c4aa7919c57a - languageName: node - linkType: hard - -"@sideway/pinpoint@npm:^2.0.0": - version: 2.0.0 - resolution: "@sideway/pinpoint@npm:2.0.0" - checksum: 0f4491e5897fcf5bf02c46f5c359c56a314e90ba243f42f0c100437935daa2488f20482f0f77186bd6bf43345095a95d8143ecf8b1f4d876a7bc0806aba9c3d2 - languageName: node - linkType: hard - "@sinclair/typebox@npm:^0.24.1": version: 0.24.51 resolution: "@sinclair/typebox@npm:0.24.51" @@ -8401,7 +8389,7 @@ __metadata: version: 0.0.0-use.local resolution: "@theatre/app@workspace:packages/app" dependencies: - "@auth0/nextjs-auth0": ^3.1.0 + "@auth/prisma-adapter": ^1.0.3 "@prisma/client": ^4.12.0 "@tanstack/react-query": ^4.32.6 "@trpc/client": ^10.38.0 @@ -8423,6 +8411,7 @@ __metadata: jsonwebtoken: ^9.0.1 nanoid: ^3.3.1 next: 13.4.13 + next-auth: ^4.23.2 npm-run-all: ^4.1.5 pg: ^8.11.2 prisma: ^4.12.0 @@ -23017,23 +23006,10 @@ fsevents@^1.2.7: languageName: node linkType: hard -"joi@npm:^17.6.0": - version: 17.9.1 - resolution: "joi@npm:17.9.1" - dependencies: - "@hapi/hoek": ^9.0.0 - "@hapi/topo": ^5.0.0 - "@sideway/address": ^4.1.3 - "@sideway/formula": ^3.0.1 - "@sideway/pinpoint": ^2.0.0 - checksum: 055df3841e00d7ed065ef1cc3330cf69097ab2ffec3083d8b1d6edfd2e25504bf2983f5249d6f0459bcad99fe21bb0c9f6f1cc03569713af27cd5eb00ee7bb7d - languageName: node - linkType: hard - -"jose@npm:^4.10.0, jose@npm:^4.9.2": - version: 4.13.1 - resolution: "jose@npm:4.13.1" - checksum: 89be959573beee69bd443493887d78799fd42340b45afa2c6681beda30314bcdfa5575f6977203c199e4c3e0ec2fc18d3c94745e7f0d59db51dedfae0efee63d +"jose@npm:^4.11.1, jose@npm:^4.11.4, jose@npm:^4.15.1": + version: 4.15.2 + resolution: "jose@npm:4.15.2" + checksum: 8f0cab1eef31243abe14a935b2b330cd95f10f9b69808fd642088ae5000e50e566664934537d2c6413ab2f6b54acd8265a5033da05157aa1260c5f1d7e57fab0 languageName: node linkType: hard @@ -25063,6 +25039,31 @@ fsevents@^1.2.7: languageName: node linkType: hard +"next-auth@npm:^4.23.2": + version: 4.23.2 + resolution: "next-auth@npm:4.23.2" + dependencies: + "@babel/runtime": ^7.20.13 + "@panva/hkdf": ^1.0.2 + cookie: ^0.5.0 + jose: ^4.11.4 + oauth: ^0.9.15 + openid-client: ^5.4.0 + preact: ^10.6.3 + preact-render-to-string: ^5.1.19 + uuid: ^8.3.2 + peerDependencies: + next: ^12.2.5 || ^13 + nodemailer: ^6.6.5 + react: ^17.0.2 || ^18 + react-dom: ^17.0.2 || ^18 + peerDependenciesMeta: + nodemailer: + optional: true + checksum: 4820fdc8d9f066afd2dfe64012d7aba727fd7b82fec3a94e85ea5c1651cb4bf532d8742bfd253d9910055833f00c1c8f8f17212661f7648ecff4dd1f3e002e80 + languageName: node + linkType: hard + "next-tick@npm:~1.0.0": version: 1.0.0 resolution: "next-tick@npm:1.0.0" @@ -25529,13 +25530,20 @@ fsevents@^1.2.7: languageName: node linkType: hard -"oauth4webapi@npm:^2.3.0": +"oauth4webapi@npm:^2.0.6": version: 2.3.0 resolution: "oauth4webapi@npm:2.3.0" checksum: abe1aa9997f8cd779b661ca60b378d50de039b624f89c0a72574c65141432bca6a319116362cae49197f687b6e08d01d76476f74545f074071cbb63303d86fab languageName: node linkType: hard +"oauth@npm:^0.9.15": + version: 0.9.15 + resolution: "oauth@npm:0.9.15" + checksum: 957c0d8d85300398dcb0e293953650c0fc3facc795bee8228238414f19f59cef5fd4ee8d17a972c142924c10c5f6ec50ef80f77f4a6cc6e3c98f9d22c027801c + languageName: node + linkType: hard + "object-assign@npm:^4, object-assign@npm:^4.0.1, object-assign@npm:^4.1.0, object-assign@npm:^4.1.1": version: 4.1.1 resolution: "object-assign@npm:4.1.1" @@ -25554,7 +25562,7 @@ fsevents@^1.2.7: languageName: node linkType: hard -"object-hash@npm:^2.0.1": +"object-hash@npm:^2.2.0": version: 2.2.0 resolution: "object-hash@npm:2.2.0" checksum: 55ba841e3adce9c4f1b9b46b41983eda40f854e0d01af2802d3ae18a7085a17168d6b81731d43fdf1d6bcbb3c9f9c56d22c8fea992203ad90a38d7d919bc28f1 @@ -25831,10 +25839,10 @@ fsevents@^1.2.7: languageName: node linkType: hard -"oidc-token-hash@npm:^5.0.1": - version: 5.0.1 - resolution: "oidc-token-hash@npm:5.0.1" - checksum: d62aa8c665f1a0133a3694785e4cd75f471364e6a2f4fbf7997e193a49ccf8f8de15596f475c7fdf8510d021c3b72f7ff6ab8bc5b07bff4cf21d490177f164a5 +"oidc-token-hash@npm:^5.0.3": + version: 5.0.3 + resolution: "oidc-token-hash@npm:5.0.3" + checksum: 35fa19aea9ff2c509029ec569d74b778c8a215b92bd5e6e9bc4ebbd7ab035f44304ff02430a6397c3fb7c1d15ebfa467807ca0bcd31d06ba610b47798287d303 languageName: node linkType: hard @@ -25927,15 +25935,15 @@ fsevents@^1.2.7: languageName: node linkType: hard -"openid-client@npm:^5.2.1": - version: 5.4.0 - resolution: "openid-client@npm:5.4.0" +"openid-client@npm:^5.4.0": + version: 5.6.0 + resolution: "openid-client@npm:5.6.0" dependencies: - jose: ^4.10.0 + jose: ^4.15.1 lru-cache: ^6.0.0 - object-hash: ^2.0.1 - oidc-token-hash: ^5.0.1 - checksum: d198dbcaf0aa1d8b9f0f1d99ae30e90ec594eaf9ae668b5d61f2ee9af94a4460968d8dea7e53bd18903a1fb9c445e05aefca965bb88be3688a4bac273d1634d9 + object-hash: ^2.2.0 + oidc-token-hash: ^5.0.3 + checksum: 414fe43c5aac07d8b8f5ea52ef1812374ff28140910977a1360781284b09d4a03c916d910017bf15003d602d859b3dcf9857d1dfe6f61508c8f5c52de334e6ea languageName: node linkType: hard @@ -28738,6 +28746,42 @@ fsevents@^1.2.7: languageName: node linkType: hard +"preact-render-to-string@npm:5.2.3": + version: 5.2.3 + resolution: "preact-render-to-string@npm:5.2.3" + dependencies: + pretty-format: ^3.8.0 + peerDependencies: + preact: ">=10" + checksum: 6e46288d8956adde35b9fe3a21aecd9dea29751b40f0f155dea62f3896f27cb8614d457b32f48d33909d2da81135afcca6c55077520feacd7d15164d1371fb44 + languageName: node + linkType: hard + +"preact-render-to-string@npm:^5.1.19": + version: 5.2.6 + resolution: "preact-render-to-string@npm:5.2.6" + dependencies: + pretty-format: ^3.8.0 + peerDependencies: + preact: ">=10" + checksum: be8d5d8fb502d422c503e68af7bcccb6facd942f3ae9a4d093ebe3f1d4f0b15c540624bdac434d53a2a8e8fb7afa4606383414e937c40933ca43445470a026ff + languageName: node + linkType: hard + +"preact@npm:10.11.3": + version: 10.11.3 + resolution: "preact@npm:10.11.3" + checksum: 9387115aa0581e8226309e6456e9856f17dfc0e3d3e63f774de80f3d462a882ba7c60914c05942cb51d51e23e120dcfe904b8d392d46f29ad15802941fe7a367 + languageName: node + linkType: hard + +"preact@npm:^10.6.3": + version: 10.18.1 + resolution: "preact@npm:10.18.1" + checksum: 691030149fdbd026cac7c07147756f48c6cb8cdea6a8af8c0f383e4c31f5bce48cdc751e4bccf8826560a0d2db77ada401c0308f2bcae2961d16972c26c95607 + languageName: node + linkType: hard + "prelude-ls@npm:^1.2.1": version: 1.2.1 resolution: "prelude-ls@npm:1.2.1" @@ -28849,6 +28893,13 @@ fsevents@^1.2.7: languageName: node linkType: hard +"pretty-format@npm:^3.8.0": + version: 3.8.0 + resolution: "pretty-format@npm:3.8.0" + checksum: 21a114d43ef06978f8f7f6212be4649b0b094f05d9b30e14e37550bf35c8ca24d8adbca9e5adc4cc15d9eaf7a1e7a30478a4dc37b30982bfdf0292a5b385484c + languageName: node + linkType: hard + "prisma@npm:^4.12.0": version: 4.12.0 resolution: "prisma@npm:4.12.0" @@ -34276,13 +34327,6 @@ fsevents@^1.2.7: languageName: node linkType: hard -"url-join@npm:^4.0.1": - version: 4.0.1 - resolution: "url-join@npm:4.0.1" - checksum: f74e868bf25dbc8be6a8d7237d4c36bb5b6c62c72e594d5ab1347fe91d6af7ccd9eb5d621e30152e4da45c2e9a26bec21390e911ab54a62d4d82e76028374ee5 - languageName: node - linkType: hard - "url-loader@npm:4.1.1": version: 4.1.1 resolution: "url-loader@npm:4.1.1"