Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

GhostvOne's avatar

NUXT 3 + SANCTUM SPA AUTH : Can't having usefetch working with Session/Cookies on SERVER SIDE ONLY

Hello How can I have usefetch working perfectly with Session/Cookies on SERVER SIDE ONLY using laravel sanctum api. It works perfectly if my middleware is client side (if process.client) but doesn't work anymore if my middleware if server side only (process.server)

If i'm using nuxt server side only Laravel is returning me this :

CSRF token mismatch.

Here my middleware


export default defineNuxtRouteMiddleware(async (to, from) => {
    // skip middleware on client
    if (process.client) return

    const code = to.query.code as string

    if (!code) {
        return navigateTo('/')
    }

    const auth = useAuthStore()

    if (auth.isLoggedIn) {
        return navigateTo('/')
    }

    await useSanctumFetch('/sanctum/csrf-cookie')
  
    const { data, error } = await useSanctumFetch('/login/discord', {
        method: 'POST',
        params: {
            code: code,
        },
    })

    const auth = useAuthStore()
    if (data.value) auth.user = data.value.user as User

    return navigateTo('/')
})

useSanctumFetch.ts

import type { UseFetchOptions } from '#app'
import { defu } from 'defu'

export const useSanctumFetch = <T>(
    url: string | (() => string),
    options?: UseFetchOptions<T>
) => {
    const auth = useAuthStore()
    const config = useRuntimeConfig().public

    function getCookie(name, data) {
        const value = `; ${data}`
        const parts = value.split(`; ${name}=`)
        if (parts.length === 2) return parts.pop().split(';').shift()
    }

    let headers = {
        ...(auth.csrfToken && {
            'X-XSRF-TOKEN': decodeURIComponent(auth.csrfToken),
        }),
        ...{
            Accept: 'application/json',
            'Content-Type': 'application/json',
            I tried this bellow
            // referer: config.appUrl,
        },
    }

    if (process.server) {
        headers = {
            ...headers,
            ...useRequestHeaders(['referer', 'cookie']),
            referer: config.appUrl,
        }
    }

    const defaults: UseFetchOptions<T> = {
        baseURL: config.apiUrl,
        credentials: 'include',
        key: typeof url === 'string' ? url : url(),
        watch: false,
        headers: headers,
        onResponse: (response) => {
            if (process.server) {
                auth.csrfToken = getCookie(
                    'XSRF-TOKEN',
                    response.response.headers.get('set-cookie') ?? ''
                )
            }

            if (process.client) {
                auth.csrfToken = useCookie('XSRF-TOKEN').value
            }
        },
    }

    const params = defu(options, defaults)
    console.log(params)

    return useFetch(url, params)
}

Nuxt .env (.. => tt)

APP_URL=h..p://localhost:3000
API_URL=h..p://localhost:8000

nuxt.config.ts

export default defineNuxtConfig({
    css: ['~/assets/css/app.css'],
    devtools: { enabled: true },
    modules: ['@nuxtjs/tailwindcss', '@pinia/nuxt'],
    runtimeConfig: {
        public: {
            appUrl: process.env.APP_URL,
            apiUrl: process.env.API_URL,
        },
    },
})

On my laravel .env I have :

SESSION_DOMAIN=localhost
SANCTUM_STATEFUL_DOMAINS=localhost:3000

cors.php

<?php

return [

//    'paths' => ['api/*', 'login/discord', 'sanctum/csrf-cookie'],
    'paths' => ['*'],

    'allowed_methods' => ['*'],

    'allowed_origins' => ['*'],

    'allowed_origins_patterns' => [],

    'allowed_headers' => ['*'],

    'exposed_headers' => [],

    'max_age' => 0,

    'supports_credentials' => true,

];

What's wrong ? Why if i'm server side with nuxt it doesn't work anymore ? I tried everything since multiple days but can't fix that.

0 likes
0 replies

Please or to participate in this conversation.