Authentication
This document describes the end-to-end authentication flow for Notebooks Hub across the UI, API, and how it integrates with the identity provider (LabShare Auth).
Environment Configuration
Configure the following environment variables with values from your LabShare Auth application:
# LabShare Auth OIDC Configuration
SERVICES_AUTH_URL='https://your-labshare-auth-domain.com'
SERVICES_AUTH_TENANT='your-tenant-identifier'
SERVICES_AUTH_CLIENT_ID='your-client-id'
SERVICES_AUTH_CLIENT_SECRET='your-client-secret'
SERVICES_AUTH_REDIRECT_URL='https://your-app-domain.com/auth/callback'
Note: Replace the placeholder values with your actual LabShare Auth configuration. The SERVICES_AUTH_REDIRECT_URL
should match the callback URL configured in your LabShare Auth application.
High-level sequence
UI calls API
/auth/authorize
to obtain an IdP authorization URL and redirects the user to the IdP (PKCE is used; the verifier is stored in the API session).After user login/consent, IdP redirects back to the UI with
code
in the URL.UI calls API
/auth/token
with thecode
. API validates the PKCEcode_verifier
from session and exchanges the code with the IdP for tokens.UI stores
access_token
,id_token
,refresh_token
, andexpires_at
locally and begins calling API endpoints withAuthorization: Bearer <access_token>
.API authenticates requests by validating the JWT and, if needed, initializes the request session profile by calling the IdP
/me
endpoint.For protected resources, API checks authorization (OpenFGA) before serving responses.
UI refreshes tokens via
/auth/refresh
when near expiry; on logout, UI calls/auth/logout
to get a provider logout URL and redirects the browser.
API endpoints (authentication)
POST /auth/authorize
- Returns an authorization URL for the IdP and stores PKCEcode_verifier
in the API session.POST /auth/token
- Exchanges the authorization code for tokens using the stored PKCE verifier.POST /auth/refresh
- Refreshes expired access tokens using the refresh token.POST /auth/logout
- Returns a logout URL pointing to the IdP end-session endpoint.
The API uses the openid-client library for OIDC operations including PKCE code generation, token exchange, and refresh flows.
API request authentication
The API configures an OAuth/JWT strategy that validates bearer tokens and ensures a valid email exists in the session profile. On each request, if the session is not initialized, the API calls the IdP
/me
endpoint with the bearer token to populate the session (email, provider, token).
Token and session details
Tokens:
access_token
is sent as a bearer token on API calls;id_token
is used for user profile;refresh_token
is used by the UI to refresh.Session: The API stores PKCE
code_verifier
and a minimal profile (email
,provider
,token
) in the server-side session per user.Scopes: Default scopes requested include
openid profile offline_access email tenant identity_provider
on the API OIDC client; JupyterHub requestsopenid profile email
.
Security considerations
Use HTTPS in all environments to protect tokens in transit.
Keep
client_secret
andrefresh_token
secure; never expose secrets in client code or logs.Limit token lifetimes and rely on refresh when necessary; the UI refreshes proactively before expiry.
Validate issuer and JWKS configuration in the API, and ensure
aud
,iss
, and signature checks are correct in the JWT validation middleware.Configure CORS and
withCredentials
appropriately so the API session is bound to the browser and cannot be replayed cross-site.
Troubleshooting Tips
Missing code_verifier Error:
If
/auth/token
fails withMissing code_verifier
, ensure the same browser session initiated/auth/authorize
and that cookies are not blocked.Verify that
Set-Cookie
headers are being set in API responses, as thecode_verifier
is persisted through session cookies for the PKCE flow.If cookies are disabled or cannot be set in the backend service, the
code_verifier
cannot be persisted through the session and login will fail.
Nonce Mismatch Error:
If
/auth/token
fails withToken exchange failed: RPError: nonce mismatch, expected undefined, got: [nonce_value]
, ensure thatLegacy application compatibility
is disabled in the Advanced features section of your LabShare Auth application configuration.