[Vuex] vue 상태 머신에 대한 자세한 설명

목차

Vuex

1. Vuex의 다섯 가지 속성

2. Vuex의 작동 원리

3. Vuex 사용

html 파일 사용

도우미 기능

모듈식 모듈 및 네임스페이스

vue-cli 스캐폴딩에서 사용


Vuex

Vuex는 Vue.js 애플리케이션을 위해 특별히 개발된 상태 관리 패턴 입니다 . 중앙 집중식 스토리지를 사용하여 애플리케이션의 모든 구성 요소 상태를 관리하고 해당 규칙을 사용하여 상태가 예측 가능한 방식으로 변경되도록 합니다.

Vuex는 통합 관리를 위해 구성 요소가 공유하는 데이터를 상태 시스템에 넣는 상태 머신이라고도 하는 상태 관리 모드입니다.구성 요소가 데이터를 가져오려면 자체 데이터 모델 또는 웨어하우스에서 가져올 수 있습니다. Vuex는 창고로 이해할 수 있습니다.

구성 요소 A가 구성 요소 B의 데이터를 가져오고 구성 요소 A와 구성 요소 B의 데이터를 Vuex에 넣고 구성 요소 A가 vuex에서 구성 요소 B의 데이터를 가져오고 구성 요소 B가 구성 요소 A의 데이터를 가져오고 싶어한다고 가정합니다. Vuex에서.

1. Vuex의 다섯 가지 속성

{
	//state 维护的是公共状态(数据),类似Vue中的data
	state: {},
	//getters 处理state中的数据并返回新数据,类似计算属性computed
	getters: {},
	//mutations 突变,修改state的唯一方式,只能做同步操作
	mutations: {},
	//actions 动作,处理异步操作,获取后台响应,提交数据给突变mutations
	actions: {},
	// 状态机可以有多个,modules用来存放各模块的状态机
	modules: {}
}

2. Vuex의 작동 원리

vuex의 세 가지 주요 속성: state, mutation, action


 

상태 머신을 선언하고 Vue 인스턴스에 주입하면 Vue 인스턴스에 $store 속성이 있으며 여기에는 dispatch 및 commit과 같은 메서드가 있습니다. 

위의 그림을 분석하십시오.

Vue 컴포넌트는 실행해야 할 메소드를 Actions에 디스패치하여 실행 하지만 Actions는 해당 메소드를 실행하지 않으므로 Commit 메소드를 통해 해당 메소드를 Mutation에 제출하여 실행합니다. 데이터는 State 로 전송되고 State는 데이터를 페이지로 다시 렌더링합니다.

참고: Vue 구성 요소가 작동해야 하는 데이터를 네트워크 요청을 통해 얻을 필요가 없는 경우 작업을 건너뛰고 commit 메서드를 사용하여 처리하기 위해 변형에 직접 제출할 수 있습니다.

3. Vuex 사용

html 파일 사용

1. CDN을 통해 Vuex 가져오기

Vuex는 Vue의 플러그인으로 사용시 설치가 필요합니다.

<script src="https://cdnjs.cloudflare.com/ajax/libs/vuex/3.6.0/vuex.min.js" integrity="sha512-uN93RUcJ9frHH6dyLknjgalFe7JNkfb3OjW4Qgg5xjaVA3U7l0diZ3hGL2Puk/38sp7xD/SLHdNFit7Kq3RbtQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

2. 상태 머신 선언

let store = new Vuex.Store(
	{
		//state 维护的是公共状态,类似Vue中的data
		state: {},
		//getters 处理state中的数据并返回新数据,类似计算属性computed
		getters: {},
		//mutations 突变,修改state的唯一方式,只能做同步操作
		mutations: {},
		//actions 动作,处理异步操作,获取后台响应,提交数据给突变mutations
		actions: {}
	}
)

3. Vue 인스턴스에 상태 머신 주입

let vm = new Vue({
	// 将状态机注入Vue实例
	store,
	el: "#app",
	data: {}
})

이 시점에서 Vue 인스턴스에서 $store를 인쇄하여 확인할 수 있습니다.

console.log(vm.$store)

 따라서 보간 구문에서 $store.state.xxx 및 $store.getters.xxx를 사용하여 상태의 데이터와 게터의 메서드에 액세스할 수 있습니다.

예:

<!DOCTYPE html>
<html lang="en">

<head>
	<meta charset="UTF-8">
	<meta http-equiv="X-UA-Compatible" content="IE=edge">
	<meta name="viewport" content="width=device-width, initial-scale=1.0">
	<title>Document</title>
	<script src="https://cdn.jsdelivr.net/npm/[email protected]"></script>
	<!-- 1、引入Vuex -->
	<script src="https://cdnjs.cloudflare.com/ajax/libs/vuex/3.6.0/vuex.min.js" integrity="sha512-uN93RUcJ9frHH6dyLknjgalFe7JNkfb3OjW4Qgg5xjaVA3U7l0diZ3hGL2Puk/38sp7xD/SLHdNFit7Kq3RbtQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>
</head>

<body>
	<div id="app">
		<!-- 使用state中的数据和getter中的方法 -->
		{
   
   {$store.state.msg}}
		{
   
   {$store.getters.MSG}}
		<hr>
		{
   
   {$store.state.sum}}
		<button @click="foo">点击加{
   
   {n}}</button>
	</div>
    <script>
	  let store = new Vuex.Store({
		state: {
			msg: 'hello',
			sum: 0
		},
		// getters用来处理state中的数据
		getters: {
			MSG(state){ //默认有一个参数,它是一个对象,里面存放了state中的数据
				// console.log(state);
				return state.msg.toUpperCase()
			}
		},
		actions: {
			// 默认有两个参数:sto是一个类状态机对象; value是dispatch传递过来的数据
			add(sto, value){
				// console.log(sto, value, 'actions');
				// 提交突变给mutations
				// commit('mutations中的方法名', 需要传递的数据)
				sto.commit('ADD', value)
			}
		},
		mutations: {
			// 最终在mutations中处理数据
			// 默认两个参数:state是一个对象,里面存放了state中的数据; value是commit提交的时候传递过来的数据
			ADD(state, value){
				// console.log(state, value, 'mutations');
				state.sum += value
			}
		},
	})

	let vm = new Vue({
		store,
		el: "#app",
		data: {
			n: 2
		},
		methods:{
			foo(){
				// 派发一个动作给actions
				// dispatch('actions中的方法名', 需要传递的数据)
				this.$store.dispatch('add', this.n)
			}
		}
	})
	// console.log(vm); //打印Vue实例,可以看到Vue实例上有一个$store属性
  </script>
</body>

</html>

도우미 기능

Vuex에서 제공하는 컴포넌트 보조 함수에는 mapState, mapGetters, mapActions 및 mapMutations가 포함되며 Vuex 객체에 존재하며 Vuex.mapState를 사용하여 호출하거나 Vuex에서 분해하여 사용할 수 있습니다.

let { mapState, mapGetters, mapActions, mapMutations } = Vuex

1. mapState 메서드: 상태의 데이터를 계산된 속성에 매핑하는 데 사용됩니다.

computed:{
	// msg(){
	// 	return this.$store.state.msg
	// },
	// sum(){
	// 	return this.$store.state.sum
	// }
	//-----------------------------------------------------
	// 借助mapState函数生成上述计算属性
	// mapState返回一个对象,我们需要使用扩展运算符将它们展开
	// 1、对象写法
	...mapState({msg:'msg',sum:'sum'})
	// 2、数组写法
	...mapState(['msg','sum'])
},
// 测试,看一下mapState返回值
created(){
	let a = mapState({msg:'msg',sum:'sum'})
	console.log(a); //返回一个对象,对象中有msg、sum方法
},

mapState 메서드를 사용한 후에는 { {$store.state.msg}}, { { $store.state.sum}을 작성하는 대신 보간 구문에서 { {msg}} , { {sum}}을 직접 사용할 수 있습니다. }, mapGetters 메서드도 마찬가지입니다.

2. mapGetters 메서드: getter의 데이터를 계산된 속성에 매핑하는 데 사용됩니다.

computed:{
	// MSG(){
	// 	return this.$store.getters.MSG
	// }
	//------------------------------------------------------
	// 借助mapGetters函数生成上述计算属性
	// 1、对象写法
	...mapGetters({MSG:'MSG'})
	// 2、数组写法
	...mapGetters(['MSG'])
},

3. mapActions 메서드: 작업이 포함된 대화 생성을 돕는 데 사용되는 메서드, 즉 $store.dispatch(xxx)를 포함하는 함수

methods:{
	// foo(){
	// 	this.$store.dispatch('add', this.n)
	// }
	//--------------------------------------------
	// 借助mapActions函数生成上述foo方法
	// mapActions返回一个对象,我们需要使用扩展运算符将它们展开
	// 1、对象写法
	...mapActions({foo:'add'}),
	// 2、数组写法   (注意:需要对象的属性名和属性值一样才能写成下面的数组形式)
	...mapActions(['foo'])
}

4. mapMutations 방법: 변형이 있는 대화를 생성하는 데 도움이 되는 방법, 즉 $store.commit(xxx)를 포함하는 함수

methods:{
	// foo(){
	// 	this.$store.commit('ADD', this.n)
	// }
	//--------------------------------------------
	// 借助mapMutations函数生成上述foo方法
	// mapMutations返回一个对象,我们需要使用扩展运算符将它们展开
	// 1、对象写法
	...mapMutations({foo:'ADD'}),
	// 2、数组写法   (注意:需要对象的属性名和属性值一样才能写成下面的数组形式)
	...mapMutations(['foo'])
	
}

참고: mapActions 및 mapMutations를 사용할 때 매개변수를 전달해야 하는 경우 템플릿이 이벤트에 바인딩될 때 매개변수를 전달해야 합니다.

<button @click="foo(n)">点击加{
   
   {n}}</button>

모듈식 모듈 및 네임스페이스

단일 상태 트리를 사용하기 때문에 애플리케이션의 모든 상태는 상대적으로 큰 개체에 집중됩니다. 응용 프로그램이 매우 복잡해지면 저장소 개체가 상당히 커질 수 있습니다. 위의 문제를 해결하기 위해 Vuex는 저장소를 모듈로 나눌 수 있도록 합니다. 각 모듈에는 자체 상태, 변이, 액션, getter 및 중첩된 하위 모듈이 있습니다. namespaced는 네임스페이스를 설정하는 것을 의미합니다.

Vuex의 모듈 속성은 각 모듈의 상태 머신을 저장하는 데 사용됩니다.

let aModule = {
	// 开启命名空间
	namespaced: true,
	state:{},
	getters:{},
	actions:{},
	mutations:{}
}
let bModule = {
	namespaced: true,
	state:{},
	getters:{},
	actions:{},
	mutations:{}
}
let store = new Vuex.Store({
	modules:{
		a:aModule,
		b:bModules
	}
})

(1) 구성 요소의 상태에서 데이터 읽기 

// 方式一:自己读取
this.$store.state.a.xxx
// 方式二:使用mapState读取  表示后面数组里面的属性是a模块的
...mapState('a',['xxx1','xxx2','xxx3'])

 (2) 구성 요소의 게터에서 데이터 읽기

// 方式一:自己读取
this.$store.getters['a/xxx']
// 方式二:使用mapGetters读取  表示后面数组里面的属性是a模块的
...mapGetters('a',['xxx1','xxx2','xxx3'])

(3) 컴포넌트에서 호출 디스패치

// 方式一:自己直接dispatch
this.$store.dispatch('a/xxx',需要传递的数据)
// 方式二:使用mapActions读取
...mapActions('a',['xxx1','xxx2','xxx3'])

(4) 컴포넌트에서 커밋 호출

// 方式一:自己直接commit
this.$store.commit('a/xxx',需要传递的数据)
// 方式二:使用mapMutations读取
...mapMutations('a',['xxx1','xxx2','xxx3'])

vue-cli 스캐폴딩에서 사용

작은 사례 작성: 로그인을 클릭하면 다른 구성 요소에서도 사용되는 토큰 값을 얻게 되므로 모든 구성 요소에서 사용할 수 있도록 토큰 값을 vuex에 저장할 수 있습니다.

1. vuex 설치

참고: vuex4 이상은 vue3에서만 사용할 수 있으며, vue2는 vuex3 버전을 사용합니다. 설치 중에 버전을 지정하지 않으면 vuex의 최신 버전이 설치됩니다.

npm i [email protected]

2. src 아래에 새 폴더 저장소를 만든 다음 로그인 관련 상태 머신을 저장하기 위해 저장소 폴더 아래에 새 폴더 로그인을 만듭니다.

src/store/index.js 

import Vue from 'vue';
import Vuex from 'vuex';
// 引入登录状态机
import login from '../store/login/login';

Vue.use(Vuex);

export default new Vuex.Store({
	state:{},
	getters:{},
	mutations:{},
	actions:{},
	modules:{
		login
	}
})

src/login/login.js

import axios from 'axios';
// 这是我登录状态机配置对象
export default {
	// 开启命名空间
	namespaced: true,
	state: {
		token: localStorage.getItem('token') || ""
	},
	gettes: {},
	mutations: {
		SET_TOKEN(state, payload) {
			state.token = payload;
			// 持久化储存 
			localStorage.setItem('token', payload)
		}
	},
	actions: {
		async login({commit}, payload) {
			// 发送异步请求
			let res = await axios.post('登录接口地址', payload)
			// console.log(res);
			commit('SET_TOKEN', res.data.data.token)
		}
	}
}

3. src 아래에 구성 요소를 저장할 새 폴더 페이지를 만듭니다.

login.vue

<template>
	<div>
		登录页面-----
		<button @click='login(obj)'>登录</button>
	</div>
</template>
<script>
import {mapActions} from 'vuex'
export default {
	data(){
		return {
			obj:{
				username:"xxx",
				password:xxx
			}
		}
	},
	methods:{
		// 分发状态机动作 发送登录请求
		...mapActions('login',['login'])
	}
}
</script>

 user.vue

<template>
	<div>
		用户页面--{
   
   {token}}
	</div>
</template>
<script>
import {mapState} from 'vuex';
export default {
	data(){
		return {}
	},
	computed:{
		...mapState('login',['token'])
	}
}
</script>

 

Supongo que te gusta

Origin blog.csdn.net/lq313131/article/details/127131901
Recomendado
Clasificación