From 102529a99fd35a8b709922380e284aadfc9c6cc1 Mon Sep 17 00:00:00 2001 From: Luke Vella Date: Wed, 28 May 2025 14:11:52 +0100 Subject: [PATCH] =?UTF-8?q?=F0=9F=90=9B=20Require=20oidc=20issuer=20url=20?= =?UTF-8?q?(#1738)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/docs/self-hosting/configuration.mdx | 12 +++++++++ .../login/components/login-with-oidc.tsx | 5 ++-- apps/web/src/auth/providers/oidc.ts | 27 ++++++++++++------- apps/web/src/env.ts | 2 ++ turbo.json | 1 + 5 files changed, 35 insertions(+), 12 deletions(-) diff --git a/apps/docs/self-hosting/configuration.mdx b/apps/docs/self-hosting/configuration.mdx index 0ee6233d9..9d01651cb 100644 --- a/apps/docs/self-hosting/configuration.mdx +++ b/apps/docs/self-hosting/configuration.mdx @@ -119,6 +119,13 @@ https:///api/auth/callback/microsoft-entra-id ### Custom SSO (OIDC) +The following must be set for OIDC to work: + +- `OIDC_DISCOVERY_URL` +- `OIDC_CLIENT_ID` +- `OIDC_CLIENT_SECRET` +- `OIDC_ISSUER_URL` + Your OAuth 2.0 application needs to be configured with the following scopes: @@ -141,6 +148,11 @@ https:///api/auth/callback/oidc URL of the `.well-known/openid-configuration` endpoint for your OIDC provider + + URL of the issuer for your OIDC provider. You can get this from your OpenId + Configuration endpoint. + + The client ID of your OIDC application diff --git a/apps/web/src/app/[locale]/(auth)/login/components/login-with-oidc.tsx b/apps/web/src/app/[locale]/(auth)/login/components/login-with-oidc.tsx index 0b3bad55a..7e74d6ad8 100644 --- a/apps/web/src/app/[locale]/(auth)/login/components/login-with-oidc.tsx +++ b/apps/web/src/app/[locale]/(auth)/login/components/login-with-oidc.tsx @@ -4,7 +4,7 @@ import { signIn } from "next-auth/react"; import { Trans } from "@/components/trans"; -export async function LoginWithOIDC({ +export function LoginWithOIDC({ name, redirectTo, }: { @@ -18,7 +18,8 @@ export async function LoginWithOIDC({ redirectTo, }); }} - variant="link" + className="w-full" + size="lg" > { - if ( - process.env.OIDC_DISCOVERY_URL && - process.env.OIDC_CLIENT_ID && - process.env.OIDC_CLIENT_SECRET - ) { + if (env.OIDC_DISCOVERY_URL && env.OIDC_CLIENT_ID && env.OIDC_CLIENT_SECRET) { + if (!env.OIDC_ISSUER_URL) { + console.warn( + "OIDC_ISSUER_URL is not set. Please set it to the issuer URL of your OpenID Connect provider.", + ); + return; + } return { id: "oidc", - name: process.env.OIDC_NAME ?? "OpenID Connect", + name: env.OIDC_NAME ?? "OpenID Connect", type: "oidc", - wellKnown: process.env.OIDC_DISCOVERY_URL, - authorization: { params: { scope: "openid email profile" } }, - clientId: process.env.OIDC_CLIENT_ID, - clientSecret: process.env.OIDC_CLIENT_SECRET, + wellKnown: env.OIDC_DISCOVERY_URL, + authorization: { + params: { + scope: "openid email profile", + }, + }, + issuer: env.OIDC_ISSUER_URL, + clientId: env.OIDC_CLIENT_ID, + clientSecret: env.OIDC_CLIENT_SECRET, idToken: true, checks: ["pkce", "state"], allowDangerousEmailAccountLinking: true, diff --git a/apps/web/src/env.ts b/apps/web/src/env.ts index 549ad90c7..19694608e 100644 --- a/apps/web/src/env.ts +++ b/apps/web/src/env.ts @@ -19,6 +19,7 @@ export const env = createEnv({ OIDC_DISCOVERY_URL: z.string().optional(), OIDC_CLIENT_ID: z.string().optional(), OIDC_CLIENT_SECRET: z.string().optional(), + OIDC_ISSUER_URL: z.string().optional(), OIDC_EMAIL_CLAIM_PATH: z.string().default("email"), OIDC_NAME_CLAIM_PATH: z.string().default("name"), OIDC_PICTURE_CLAIM_PATH: z.string().default("picture"), @@ -104,6 +105,7 @@ export const env = createEnv({ OIDC_DISCOVERY_URL: process.env.OIDC_DISCOVERY_URL, OIDC_CLIENT_ID: process.env.OIDC_CLIENT_ID, OIDC_CLIENT_SECRET: process.env.OIDC_CLIENT_SECRET, + OIDC_ISSUER_URL: process.env.OIDC_ISSUER_URL, OIDC_EMAIL_CLAIM_PATH: process.env.OIDC_EMAIL_CLAIM_PATH, OIDC_NAME_CLAIM_PATH: process.env.OIDC_NAME_CLAIM_PATH, OIDC_PICTURE_CLAIM_PATH: process.env.OIDC_PICTURE_CLAIM_PATH, diff --git a/turbo.json b/turbo.json index 7c3c59ef1..9838a02ef 100644 --- a/turbo.json +++ b/turbo.json @@ -90,6 +90,7 @@ "NOREPLY_EMAIL", "OIDC_CLIENT_ID", "OIDC_CLIENT_SECRET", + "OIDC_ISSUER_URL", "OIDC_DISCOVERY_URL", "OIDC_EMAIL_CLAIM_PATH", "OIDC_NAME_CLAIM_PATH",