vuex 介绍
Vuex 是一个专为 Vue.js 应用程序开发的状态管理
模式 + 库。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。
初始化项目
- 使用 vue create my-vuex
- 安装 vuex:npm i vuex
- 安装 vue-router:npm i vue-vue-router
使用 vuex
// ./src/main.js
import { createApp } from "vue";
import App from "./App.vue";
import router from "./router";
import store from "./store";
const app = createApp(App);
app.use(router);
app.use(store);
app.mount("#app");
开始使用
文件目录
|-- ./src
| |-- ./src/App.vue
| |-- ./src/main.js
| |-- ./src/router
| | `-- ./src/router/index.js
| |-- ./src/store
| | |-- ./src/store/index.js
| | `-- ./src/store/modules
| | `-- ./src/store/modules/about.js
| `-- ./src/views
| |-- ./src/views/AboutView.vue
| `-- ./src/views/HomeView.vue
<!-- ./src/App.vue -->
<script setup>
import { RouterLink, RouterView } from "vue-router";
</script>
<template>
<header>
<div class="wrapper">
<h1>App组件</h1>
<!-- template 中获取 状态 -->
<h3>APP 当前计数:{{ $store.state.count }}</h3>
<hr color="red" />
<section>
<nav>
<RouterLink to="/">Home</RouterLink>
<RouterLink to="/about">About</RouterLink>
</nav>
</section>
</div>
</header>
<RouterView />
</template>
<style scoped>
nav a.router-link-exact-active {
color: red;
}
a {
margin-left: 20px;
}
</style>
// ./src/router/index.js
import { createRouter, createWebHistory } from "vue-router";
import HomeView from "../views/HomeView.vue";
const router = createRouter({
history: createWebHistory(import.meta.env.BASE_URL),
routes: [
{
path: "/",
name: "home",
component: HomeView,
},
{
path: "/about",
name: "about",
component: () => import("../views/AboutView.vue"),
},
],
});
export default router;
// ./src/store/index.js
import { createStore } from "vuex";
import aboutModule from "./modules/about";
const store = createStore({
modules: {
about: aboutModule,
},
state: () => ({
count: 10,
name: "hahaha",
age: 18,
names: [
{ id: 1, name: "a" },
{ id: 2, name: "b" },
{ id: 3, name: "c" },
],
// 服务器中的数据
data: [],
}),
/**
* mutation的重要原则:
* 1.mutation 必须是同步函数
* 因为 devtool工具会记录 mutation的日志;
* 每一条 mutation被记录,devtools都需要捕捉到前一个状态和后一个状态的快照;
* 但是mutation中执行异步操作,就无法追踪到数据的变化
*
*/
mutations: {
increment(state) {
state.count++;
},
changeName(state) {
state.name = "你好啊";
},
changeAge(state, age) {
state.age += age;
},
changeData(state, data) {
state.data = data;
},
},
// 某些数据经过变化进行使用
getters: {
formatName(state) {
return state.name.toLocaleUpperCase();
},
message(state, getters) {
// 可以获取到 gerters
return `${getters.formatName}` + state.age;
},
getName(state) {
return function (id) {
const nameRes = state.names.find((item) => item.id === id);
return nameRes;
};
},
},
actions: {
incrementAction(context) {
// contetx 中有 commit,dispatch,getters,rootGetters,rootState,state
context.commit("increment");
},
fetchHomeMutidataAction(context) {
fetch("https://jsonplaceholder.typicode.com/users")
.then((res) => {
return res.json();
})
.then((data) => {
console.log(data, "---");
context.commit("changeData", data);
});
},
},
});
export default store;
// ./src/store/modules/about.js
export default {
state: () => ({
about: "about------state",
}),
};
./src/views/AboutView.vue
<script setup></script>
<template>
<div class="about">
<h2>About 页面</h2>
<h3>{{ $store.state.about.about }}</h3>
</div>
</template>
<style></style>
<!-- ./src/views/HomeView.vue -->
<script setup>
import { toRefs } from "vue";
import { useStore } from "vuex";
const store = useStore();
// 发起网络请求
store.dispatch("fetchHomeMutidataAction");
const { data } = toRefs(store.state);
</script>
<template>
<main>
<h2>Home 页面</h2>
<ul v-if="data.at(-1)">
<template
v-for="item in data"
:key="item.id"
>
<li>{{ item.username }}</li>
</template>
</ul>
<h3 v-else>loading...</h3>
</main>
</template>