Vue3项目中使用Pinia代替TP6 session传递

1 阅读1分钟

前后端分离架构下,Vue 无法直接读取 PHP 的 Session,Session 仅适合后端内部使用,推荐使用Pinia代替。具体实现步骤如下:

1. 后端:在登录成功时返回用户名

你的接口已经返回了 $user 数据,确保 data 中包含 username 字段即可:

// 登录成功,返回用户信息
return json([
    'code' => 200, 
    'msg' => '登录成功', 
    'data' => [
        'username' => $user->username,
        'id' => $user->id,
        // 其他需要的字段...
    ]
]);

2. 前端:登录页接收并存入 Pinia

安装 Pinia(如未安装):

npm install pinia

创建用户 Store(src/stores/user.ts):

import { defineStore } from 'pinia'
import { ref } from 'vue'

export const useUserStore = defineStore('user', () => {
  const username = ref('')

  function setUsername(name: string) {
    username.value = name
    localStorage.setItem('username', name) // 同时持久化,刷新不丢失
  }

  function clearUser() {
    username.value = ''
    localStorage.removeItem('username')
  }

  return { username, setUsername, clearUser }
})

在登录页调用:

import { useUserStore } from '@/stores/user'
import { useRouter } from 'vue-router'

const userStore = useUserStore()
const router = useRouter()

async function handleLogin() {
  const res = await api.post('/login', { username, password })
  if (res.data.code === 200) {
    // 将后端返回的用户名存入 Pinia
    userStore.setUsername(res.data.data.username)
    // 跳转到首页
    router.push('/home')
  }
}

3. Home 页面:读取用户名展示

<template>
  <div>
    <p>欢迎回来,{{ userStore.username }}</p>
    <button @click="logout">退出登录</button>
  </div>
</template>

<script setup lang="ts">
import { useUserStore } from '@/stores/user'
import { useRouter } from 'vue-router'

const userStore = useUserStore()
const router = useRouter()

function logout() {
  userStore.clearUser()
  router.push('/login')
}
</script>

4. 路由守卫:防止未登录访问 Home

在 src/router/index.ts 中添加全局前置守卫:

router.beforeEach((to, from, next) => {
  const token = localStorage.getItem('username') // 或用 token 判断
  if (to.path === '/home' && !token) {
    next('/login')
  } else {
    next()
  }
})

⚠️ 关于 Session 的补充说明

后端代码中的 Session::set('user_name', $username) 依然保留即可,它有以下作用:

  • 后端鉴权:后续接口可通过 Session::get('user_name') 判断用户是否登录
  • 服务端逻辑:如记录操作日志、权限校验等

但在前后端分离场景下,前端无法直接读取 PHP Session,所以用户名必须通过 JSON 响应显式返回给前端。如果你需要跨域请求时保持 Session,还需在 axios 中配置 withCredentials: true,并确保后端 CORS 配置允许携带凭证。