Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Laravel Sanctum : blocked by CORS policy with Nuxt Auth module

I have a Laravel website served by Valet on backend.test and a Nuxt SPA on nuxt.backend.test:3005. When I try to authenticate to Sanctum with Nuxt Auth module, I get the CORS error below:

Access to XMLHttpRequest at 'http://backend.test/login' from origin 'http://nuxt.backend.test:3005' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.

How can I fix it ?

Laravel configuration

config/cors.php:

<?php

return [
    'paths' => ['*'],
    'allowed_methods' => ['*'],
    'allowed_origins' => ['*'],
    'allowed_origins_patterns' => [],
    'allowed_headers' => ['*'],
    'exposed_headers' => [],
    'max_age' => 0,
    'supports_credentials' => true,
];

routes/api.php:

Route::middleware('auth:sanctum')->get('/user', function (Request $request) {
    return $request->user();
});

app/Http/Kernel.php:

    protected $middlewareGroups = [
        ...
        'api' => [
            EnsureFrontendRequestsAreStateful::class,
            'throttle:60,1',
            \Illuminate\Routing\Middleware\SubstituteBindings::class,
        ],
    ];

.env:

SANCTUM_STATEFUL_DOMAINS="backend.test"
SESSION_DOMAIN=".backend.test"

Nuxt configuration nuxt.config.js:

export default {
  server: {
    port: '3005',
    host: 'nuxt.backend.test'
  },
  ...
  modules: [
    '@nuxtjs/axios',
    '@nuxtjs/auth-next'
  ],
  axios: {
    proxy: true
  },
  proxy: {
    '/nuxt': {
      target: 'nuxt.backend.test',
      pathRewrite: { '^/nuxt': '/' }
    }
  },
  auth: {
    redirect: {
      callback: '/auth/callback'
    },
    strategies: {
      laravelSanctum: {
        provider: 'laravel/sanctum',
        url: 'http://backend.test'
      }
    }
  },
  ...
}

pages/index.php:

<template>
  <div>
    <div>
      <pre>{{ $auth.user }}</pre>
    </div>
    <button @click="signIn()">Sign in</button>
  </div>
</template>

<script>
export default {
  methods: {
    signIn() {
      this.$auth.loginWith('laravelSanctum', {
        data: {
          email: '[email protected]',
          password: '1qaz@WSX'
        }
      })
    }
  }
}
</script>
like image 305
DevonDahon Avatar asked May 31 '20 11:05

DevonDahon


1 Answers

Laravel backend and Nuxt frontend have to be under the same domain, so I finally fixed it in 3 steps:

1. Add this to /etc/hosts:

127.0.0.1   nuxt.backend.test

2. Using the beta version of @nuxt/auth:

npm remove @nuxtjs/auth
npm install @nuxtjs/auth-next @nuxtjs/axios

In nuxt.config.js, use:

  modules: [
    '@nuxtjs/axios',
    '@nuxtjs/auth-next'
  ],

3. Using the configuration below:

{
  axios: {
    proxy: true
  },
  proxy: {
    '/laravel': {
      target: 'http://backend.test',
      pathRewrite: { '^/laravel': '/' }
    }
  },
  auth: {
    strategies: {
      laravelSanctum: {
        provider: 'laravel/sanctum',
        url: '/laravel'
      }
    }
  }
}

Alternatively, replacing backend.test and nuxt.backend.test by localhost and removing Nuxt server host from nuxt.config.js and then use php artisan serve instead of Valet for Laravel is fine too.

like image 114
DevonDahon Avatar answered Nov 04 '22 15:11

DevonDahon