当前位置:首页 > VUE

laravel vue实现登录

2026-01-08 07:03:51VUE

Laravel 和 Vue.js 实现登录功能

后端配置(Laravel)

安装 Laravel Sanctum 用于 API 认证

composer require laravel/sanctum
php artisan vendor:publish --provider="Laravel\Sanctum\SanctumServiceProvider"
php artisan migrate

config/auth.php 中设置 API 守卫

'guards' => [
    'api' => [
        'driver' => 'sanctum',
        'provider' => 'users',
    ],
],

创建登录路由(routes/api.php

use App\Http\Controllers\AuthController;

Route::post('/login', [AuthController::class, 'login']);

创建 AuthController

php artisan make:controller AuthController

实现登录逻辑(app/Http/Controllers/AuthController.php

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

public function login(Request $request)
{
    $credentials = $request->validate([
        'email' => 'required|email',
        'password' => 'required',
    ]);

    if (Auth::attempt($credentials)) {
        $user = Auth::user();
        $token = $user->createToken('auth_token')->plainTextToken;

        return response()->json([
            'access_token' => $token,
            'token_type' => 'Bearer',
        ]);
    }

    return response()->json(['error' => 'Invalid credentials'], 401);
}

前端配置(Vue.js)

安装 Axios 进行 HTTP 请求

npm install axios

创建登录组件(resources/js/components/Login.vue

<template>
  <div>
    <input v-model="email" type="email" placeholder="Email">
    <input v-model="password" type="password" placeholder="Password">
    <button @click="login">Login</button>
  </div>
</template>

<script>
import axios from 'axios';

export default {
  data() {
    return {
      email: '',
      password: ''
    }
  },
  methods: {
    async login() {
      try {
        const response = await axios.post('/api/login', {
          email: this.email,
          password: this.password
        });

        localStorage.setItem('auth_token', response.data.access_token);
        axios.defaults.headers.common['Authorization'] = `Bearer ${response.data.access_token}`;

        this.$router.push('/dashboard');
      } catch (error) {
        console.error('Login failed:', error.response.data);
      }
    }
  }
}
</script>

配置 Axios 默认设置(resources/js/app.js

import axios from 'axios';
window.axios = axios;

const token = localStorage.getItem('auth_token');
if (token) {
    axios.defaults.headers.common['Authorization'] = `Bearer ${token}`;
}

保护路由

创建中间件来验证 API 请求(app/Http/Middleware/AuthenticateAPI.php

public function handle($request, Closure $next)
{
    if (!Auth::guard('sanctum')->check()) {
        return response()->json(['message' => 'Unauthorized'], 401);
    }

    return $next($request);
}

Kernel.php 中注册中间件

protected $routeMiddleware = [
    'auth.api' => \App\Http\Middleware\AuthenticateAPI::class,
];

保护路由(routes/api.php

Route::middleware('auth.api')->group(function () {
    Route::get('/user', function () {
        return Auth::user();
    });
});

Vue 路由保护

创建路由守卫(resources/js/router/index.js

router.beforeEach((to, from, next) => {
    if (to.matched.some(record => record.meta.requiresAuth)) {
        if (!localStorage.getItem('auth_token')) {
            next({ path: '/login' });
        } else {
            next();
        }
    } else {
        next();
    }
});

标记需要认证的路由

{
    path: '/dashboard',
    component: Dashboard,
    meta: { requiresAuth: true }
}

注销功能

后端路由(routes/api.php

Route::post('/logout', [AuthController::class, 'logout']);

实现注销方法(AuthController.php

public function logout(Request $request)
{
    $request->user()->currentAccessToken()->delete();
    return response()->json(['message' => 'Logged out']);
}

前端注销按钮(Dashboard.vue

<button @click="logout">Logout</button>

methods: {
    async logout() {
        await axios.post('/api/logout');
        localStorage.removeItem('auth_token');
        delete axios.defaults.headers.common['Authorization'];
        this.$router.push('/login');
    }
}

跨域配置

config/cors.php 中配置

'paths' => ['api/*'],
'allowed_methods' => ['*'],
'allowed_origins' => ['http://localhost:8080'],
'allowed_headers' => ['*'],

.env 中设置会话域

laravel vue实现登录

SESSION_DOMAIN=localhost
SANCTUM_STATEFUL_DOMAINS=localhost:8080

标签: laravelvue
分享给朋友:

相关文章

vue实现tag

vue实现tag

Vue 实现标签(Tag)功能 在 Vue 中实现标签(Tag)功能可以通过多种方式完成,以下是一些常见的方法和实现步骤: 使用动态组件和 v-for 通过 v-for 指令动态渲染标签列表,结合样…

分页实现vue

分页实现vue

分页实现(Vue) 在Vue中实现分页功能通常需要结合前端分页逻辑和后端API支持。以下是两种常见的实现方式: 前端分页实现 适用于数据量较小的情况,直接在客户端完成分页逻辑。 <templ…

vue实现抖动

vue实现抖动

Vue 实现抖动效果 在 Vue 中实现抖动效果可以通过 CSS 动画或 JavaScript 动画库来实现。以下是几种常见的方法: 使用 CSS 动画 通过定义 @keyframes 动画并在 V…

vue 菜单实现

vue 菜单实现

Vue 菜单实现方法 在Vue中实现菜单功能可以通过多种方式完成,以下是几种常见的实现方法: 使用v-for动态生成菜单 通过数据驱动的方式动态渲染菜单项,适合菜单内容可能变化的场景: <t…

vue实现录音

vue实现录音

Vue 实现录音功能 在 Vue 中实现录音功能可以通过浏览器提供的 MediaRecorder API 完成。以下是具体实现方法: 引入依赖 确保项目支持现代浏览器 API,无需额外安装库。若需兼…

vue实现联动

vue实现联动

Vue 实现联动效果 联动效果通常指多个组件或表单元素之间相互影响,例如选择省份后动态加载城市列表。Vue 提供了多种方式实现联动,包括数据绑定、计算属性、侦听器等。 数据驱动联动 通过 Vue 的…