- 首页
- 前端开发
- 如何在 Vue 状态更改时更改路由器呈现的组件?
如何在 Vue 状态更改时更改路由器呈现的组件?
[英] How to change component rendered by router on state change in Vue?
本文介绍了如何在 Vue 状态更改时更改路由器呈现的组件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我在 Vue 中设置了一个 Vuex 商店和路由器.根据此商店中的一段状态,我希望路由器为同一路径呈现不同的组件.以下是我尝试这样做的结果.
在我的路由器中,我包含一个条件,表示如果用户已登录,则返回 Home
,否则返回 Login
".
在我的 Login
组件中,当用户成功登录时,我将 loggedIn
状态(在 Vuex 存储中)的值更改为 true在.我已经测试并可以看到此状态正在更新,但 Home
组件不会在此状态更改时呈现 - 它保持为 Login
.
登录.vue
<div className = "容器><div className = 登录"><div className = 内部登录"><div className = "title-outer><div className = "title-inner><h1 className = "reg-title title>Tweeter</h1><span className = "slogan">Twitter,但没有那么好.</span>
<div className = "form-outer><form className = 登录表单";v-on:submit="submitForm"><input @input="updateUsername";类型=文本"id=用户名"名称=用户名"占位符=用户名"需要/><br/><input @input="updatePassword";类型=密码"id="密码"名称=密码"占位符=密码"需要/><br/><输入类型=提交"值=登录"/><div className = "wrongCreds>抱歉,用户名或密码不正确.</div></表单><a className = "register-but";to=/register">创建一个账户</a><span className = "guestButton>继续作为访客 ></span>
</模板><脚本>从'../services/login.js' 导入 loginService导出默认{name: '登录',计算:{登录() {返回 this.$store.getters.loggedIn}},方法: {更新用户名:函数(事件){this.$store.commit('更改', {名称:用户名",值:事件.目标.值})},更新密码:函数(事件){this.$store.commit('更改', {名称:密码",值:事件.目标.值})},异步提交表单(e){e.preventDefault()等待 loginService.login(this.$store.getters.username, this.$store.getters.password).then(数据=> {控制台日志(数据)this.$store.commit('更改', {名称:登录",值:真})console.log(this.$store.getters.loggedIn)}).catch(错误=> {控制台日志(错误)})}}}
router.js
import { createRouter, createWebHistory } from 'vue-router'从../store/store"导入商店从../Home.vue"导入 Home从../Login.vue"导入登录const 路由器 = createRouter({历史记录:createWebHistory(),路线:[{路径:'/',组件:函数(){console.log(store.getters.loggedIn)如果(store.getters.loggedIn){回家}别的 {返回登录}}}]})导出默认路由器
store.js
import { createStore } from 'vuex';const store = createStore({状态: {用户名: '',密码: '',登录:假},突变:{变化(状态,变化){状态[theChange.name] = theChange.value},arrayItemChange(state, theChange) {状态[theChange.name][theChange.index] = theChange.value}},吸气剂:{用户名:状态 =>状态.用户名,密码:状态 =>状态.密码,登录:状态 =>状态.登录}})导出默认存储
解决方案
最佳实践以及你应该在这里做的是使用 导航守卫.
现在,为了加快速度,您需要设置 2 个导航守卫来检查用户是否已通过身份验证.
index.js(路由器文件)
const ifNotAuthenticated = (to, from, next) =>{如果(!store.getters.loggedIn){下一个();返回;}下一个(/");};const ifAuthenticated = (to, from, next) =>{如果(store.getters.loggedIn){下一个();返回;}下一个(/登录");};const 路由 =[{路径:/home",名称:家",组件:首页,beforeEnter:如果已验证,},{路径:/登录",名称:登录",组件:登录,beforeEnter: ifNotAuthenticated,}]
beforeEnter 这里是知道一个经过身份验证的用户是应该继续到下一个页面还是去登录的关键.
I have setup a Vuex store and router in Vue. Depending on a piece of state within this store, I would like the router to render a different component for the same path. Below is my attempt at doing this.
Within my router, I include a conditional that is saying "if the user is logged in, return Home
, otherwise return Login
".
Within my Login
component, I change the value of my loggedIn
state (within the Vuex store) to true when the user successfully logs in. I have tested and can see this state is being updated, but the Home
component is not being rendered upon this state change - it remains as Login
.
Login.vue
<template>
<div className = "container">
<div className = "sign-in">
<div className = "inner-sign-in">
<div className = "title-outer">
<div className = "title-inner">
<h1 className = "reg-title title">Tweeter</h1>
<span className = "slogan">Twitter, but not as good.</span>
</div>
</div>
<div className = "form-outer">
<form className = "sign-in-form" v-on:submit="submitForm">
<input @input="updateUsername" type="text" id="username" name="username" placeholder="Username" required/><br/>
<input @input="updatePassword" type="password" id="password" name="password" placeholder="Password" required/><br/>
<input type="submit" value="Login"/>
<div className = "wrongCreds">Sorry, incorrect username or password.</div>
</form>
<a className = "register-but" to="/register">Create an Account</a>
<span className = "guestButton">Continue as Guest ></span>
</div>
</div>
</div>
</div>
</template>
<script>
import loginService from '../services/login.js'
export default {
name: 'Login',
computed: {
loggedIn() {
return this.$store.getters.loggedIn
}
},
methods: {
updateUsername: function(event) {
this.$store.commit('change', {
name: "username",
value: event.target.value
})
},
updatePassword: function(event) {
this.$store.commit('change', {
name: "password",
value: event.target.value
})
},
async submitForm(e) {
e.preventDefault()
await loginService.login(this.$store.getters.username, this.$store.getters.password)
.then(data => {
console.log(data)
this.$store.commit('change', {
name: "loggedIn",
value: true
})
console.log(this.$store.getters.loggedIn)
})
.catch(error => {
console.log(error)
})
}
}
}
</script>
router.js
import { createRouter, createWebHistory } from 'vue-router'
import store from "../store/store"
import Home from "../Home.vue"
import Login from "../Login.vue"
const router = createRouter({
history: createWebHistory(),
routes: [
{ path: '/', component: function () {
console.log(store.getters.loggedIn)
if(store.getters.loggedIn) {
return Home
}
else {
return Login
}
}}
]
})
export default router
store.js
import { createStore } from 'vuex';
const store = createStore({
state: {
username: '',
password: '',
loggedIn: false
},
mutations: {
change(state, theChange) {
state[theChange.name] = theChange.value
},
arrayItemChange(state, theChange) {
state[theChange.name][theChange.index] = theChange.value
}
},
getters: {
username: state => state.username,
password: state => state.password,
loggedIn: state => state.loggedIn
}
})
export default store
解决方案
The best practice and what you should do here is to use Navigation Guards.
Now, to speed you up, you need to set 2 navigation guards which checks if user is authenticated.
index.js (router file)
const ifNotAuthenticated = (to, from, next) => {
if (!store.getters.loggedIn) {
next();
return;
}
next("/");
};
const ifAuthenticated = (to, from, next) => {
if (store.getters.loggedIn) {
next();
return;
}
next("/login");
};
const routes =[
{
path: "/home",
name: "Home",
component: Home,
beforeEnter: ifAuthenticated,
},
{
path: "/login",
name: "Login",
component: Login,
beforeEnter: ifNotAuthenticated,
}
]
beforeEnter here is the key to know whether an authenticated user should proceed to the next page or go to login.
这篇关于如何在 Vue 状态更改时更改路由器呈现的组件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文