How can I programatically authenticate a user in Auth.js?

I have a Django application with authenticated (logged-in) users.

I have another (Svelte) application using Auth.js (https://authjs.dev) for authentication, currently set up with github/facebook/linkedin.

Now I want to send a user from the Django application to the Svelte application, and automagically (i) create the user in the Svelte application if they don't exist, and (ii) log them in to the Svelte application.

I want the end-user experience to be like a regular redirect from one page to the other staying logged-in in both places.

I'm stuck at the part where the user arrives in the Svelte application and I need to create a session. Does Auth.js have any way of doing this without going through a "provider"?

I am not sure how you are maintaining the users in backend. Both your Django and Svelet app should be referring to the same user table on authjs. In that case simply passing the auth Headers should be sufficient.

The Django app generates a signed, secure token and redirects the user to the Svelte app, passing the token as part of the URL or a POST body. The Svelte app validates the token with Django.

To implement this use a secure method to generate a token in Django. You can use itsdangerous, a built-in Django signing module, or JWTs.

In your Svelte app's SSO endpoint (routes/api/sso/+server.ts), create a session for the user using Auth.js's session management.

Auth.js sessions rely on cookies. After creating or updating the user in the Svelte app, you can use Auth.js's built-in cookies to manage the session.

Here are the amended codes:

import { redirect } from '@sveltejs/kit';
import { verifyTokenWithDjango } from '$lib/auth'; // Token validation helper
import { prisma } from '$lib/server/prisma'; // Database helper
import { createSession } from '$lib/server/auth'; // Auth.js session helper

export async function GET({ url, cookies }) {
    // Extract query parameters
    const token = url.searchParams.get('token');
    const next = url.searchParams.get('next') || '/';

    // Validate inputs
    if (!token) throw new Error('SSO token is required');
    if (!next) throw new Error('The "next" parameter is required');

    // Step 1: Validate the token with Django
    const userInfo = await verifyTokenWithDjango(token);
    if (!userInfo) {
        throw new Error('Invalid or expired SSO token');
    }

    // Extract user info from the validated token
    const { email, username, name, image } = userInfo;

    // Step 2: Create or update the user in database
    const user = await prisma.user.upsert({
        where: { email },
        update: { username, name, image },
        create: { email, username, name, image }
    });

    // Step 3: Create a session using Auth.js - compatible logic
    const { sessionToken, sessionExpires } = await createSession(user, cookies);

    // Step 4: Set the session token in the cookies
    cookies.set('authjs.session-token', sessionToken, {
        path: '/',
        httpOnly: true,
        secure: true,
        sameSite: 'strict',
        expires: sessionExpires
    });

    // Step 5: Redirect to next page
    return redirect(307, next);
}

Back to Top