使用 axios GET 时未设置 CSRF Cookie - Laravel 9 Sanctum

问题描述 投票:0回答:0

我目前正在尝试使用 Laravel (v9.52.4) 和 Sanctum 创建一个简单的身份验证功能。从前端我目前使用 Axios 来获取和发布数据。前端和后端 API 都在本地主机 (http://121.0.0.1:8000) 上运行,但 API 端点可以在http://121.0.0.1:8000/api/v1/{endpoint 这里}

当我尝试登录时,一切似乎都按预期运行,但是 后端 API 没有发送/设置 CSRF cookie。 如果我使用正确的登录凭据(电子邮件 + 密码),令牌将在后端生成,存储在数据库中并发送登录成功的响应 - 当然,如果凭据无效,则不会生成令牌,我会收到正确的响应。 (因此登录逻辑似乎工作正常,但没有 CSRF cookie,我无法在管理子页面上授权自己,因此即使成功登录后它也会将我重定向到登录页面)

我一直在寻找解决方案,但到目前为止还没有运气。您可以找到可能与此问题相关的所有文件/代码片段:

.env(ROOT_URL 变量用于在前端创建 HTML 和 Javascript URL)

APP_URL=http://127.0.0.1:8000
...
SESSION_DOMAIN = "127.0.0.1:8000"
SANCTUM_STATEFUL_DOMAINS = "127.0.0.1:8000"
ROOT_URL="http://127.0.0.1:8000"

.AuthController - /login 路由使用此控制器的功能

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Http\Response;

class AuthController extends Controller
{
    public function login(Request $request){
        $credentials = [
            'email' => $request->email, 
            'password' => $request->password
        ];

        if(Auth::attempt($credentials)){
            $authUser = Auth::user();
            $success['token'] = $authUser->createToken('APIToken')->plainTextToken;
            $success['name'] = $authUser->name;
            return response()->json(['user' => $success], 200);
        }
        else {
            return response()->json(['error' => "Unauthenticated"], 404);
        }
    }

    public function logout(Request $request, $isAPI = true){
        $request->session()->invalidate();
        $request->session()->regenerateToken();

        auth()->user()->tokens()->delete();
        if($isAPI){
            return response()->json(['msg' => "user logged out"], 200);
        }
        return view('admin.login');
    }
}

cors.php

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

    'allowed_methods' => ['*'],

    'allowed_origins' => ['*'],

    'allowed_origins_patterns' => [],

    'allowed_headers' => ['*'],

    'exposed_headers' => [],

    'max_age' => 0,

    'supports_credentials' => true,

Kernel.php(我导入并添加了中间件)

...        
'api' => [
            \Laravel\Sanctum\Http\Middleware\EnsureFrontendRequestsAreStateful::class,
            'throttle:api',
            \Illuminate\Routing\Middleware\SubstituteBindings::class,
        ],
...

前端 Axios 处理程序

const API_ROOT = `${ROOT_URL}/api/v1`
axios.defaults.withCredentials = true

async function loginUser(credentials){ //these credentials are coming from the HTML form inputs
    const CSRF = `${ROOT_URL}/sanctum/csrf-cookie`
    const LOGIN_URL = `${API_ROOT}/login`

    toggleLoader()
    await axios.get(CSRF)
    await axios.post(LOGIN_URL, credentials)
        .then((res) => handleResponse(res.data))
        .catch((err) => console.log(err))
        .finally(() => toggleLoader())
}

function handleResponse(response){
    if(response.user){
        console.log(`Logged in as ${response.user.name}`)
        window.location.replace(`${ROOT_URL}/admin`)
        return
    }
    console.log('failed to log in')
}

我真的希望有人已经遇到过这个问题并且可以帮助我。谢谢大家的任何帮助或建议!

祝你有美好的一天!

旁注:当我使用 XAMPP 进行本地托管时,身份验证过程(创建令牌、设置 cookie 和登录)正在运行。然后我将项目移出 htdocs 目录并开始使用 php artisan serve 命令进行托管。除了设置 CSRF cookie 之外,其他一切(数据库、路由等)仍在工作。

laravel cookies axios csrf sanctum
© www.soinside.com 2019 - 2024. All rights reserved.