Vue Vite, Vuex, Pinia

변승훈·2022년 6월 15일
0

1. Vue Vite

vite는 현재 사용하는 프론트엔드 개발에서 웹팩을 중심으로 개발 환경과 배포 시스템이 구축되어 있는데, 이 웹팩을 사용할 때 보다 훨씬 더 빠르게 개발하고 배포할 수 있기 때문에 등장한 javascript 네이티브 모듈을 기반으로 한 dev server이다.
웹팩은 하나 하나 다 설정을 해줘야 하는 반면 vite를 이용하면 어느정도 기본 세팅이 되어 있기 때문에 사용하기 편리하다.

1. 설치

npm create vite@latest 폴더이름

현재 vue만 진행 중이므로 vue만 연속 2번 선택
이후 만든 폴더 이름으로 들어가서 code . -r로 프로젝트를 연다.

실행은 npm run dev로 되게끔 세팅이 되어 있다.

2. option

option을 설정하려면 아래의 사이트에 가서 어떻게 사용하는지 확인을 해서 사용을 하면 된다.

https://vitejs.dev/config/

vite.config.js파일에 들어가서 option을 설정하면 된다.
예를들어 경로를 ./가 아닌 ~/로 사용하기 위해 아래와 같이 resolve.alias를 설정 해보자.

import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'

// https://vitejs.dev/config/
export default defineConfig({
  plugins: [vue()],
  resolve: {
    alias: [
      { find: '~', replacement: `${__dirname}/src` }
    ]
  }
})

이후 추가적으로 eslint를 사용하려면

  1. npm i -D eslint eslint-plugin-vue로 설치해준다.
  2. ctrl + shift + p를 누르고 settings.json파일을 열어 아래의 코드가 필수적으로 있어야 한다.
"editor.codeActionsOnSave": {
	"source.fixAll.eslint": true
},
"eslint.alwaysShowStatus": true
  1. Vscode에서 eslint 확장 프로그램을 설치해주고 동작을 시켜준다.

그리고 .eslintrc.json(rc는 숨김 파일)에 옵션을 설정해 주면 된다.
아래는 수업 때 사용하는 예시이다. (코드 뒤에 세미콜론 사용x 등..)

{
  "env": {
    "browser": true,
    "node": true
  },
  "extends": [
    "eslint:recommended",
    "plugin:vue/vue3-recommended"
  ],
  "rules": {
    "semi": ["error", "never"],
    "quotes": ["error", "single"],
    "eol-last": ["error", "always"],

    "vue/html-closing-bracket-newline": ["error", {
      "singleline": "never",
      "multiline": "never"
    }],
    "vue/html-self-closing": ["error", {
      "html": {
        "void": "always",
        "normal": "never",
        "component": "always"
      },
      "svg": "always",
      "math": "always"
    }],
    "vue/comment-directive": "off",
    "vue/multi-word-component-names": "off"
  }
}

추가적으로 Vue 문법을 이해하기 위해 Vue Language Features(Volar) 확장 프로그램을 설치하면 보기가 편해진다.

2. Vuex

※ Vue Vite를 이용하여 사용한다.

vuex는 store를 사용하기 위해 쓰는 plugin이다.

1. 설치

npm install vuex

import { createStore } from 'vuex'를 통해 createStore를 불러와서 실행을 한다.
그리고 app.use(store)(플러그인)로 연결하여 사용한다.

사용시 편리성을 위해 모듈로 분리(별도의 파일로 만들기)하여 사용하는 것이 좋다.

store를 연결하기 위해 main.js에 다음과 같이 코드를 작성 해준다.

// src/main.js
import { createApp } from 'vue'
import App from './App.vue'
import store from './store'

createApp(App)
  .use(store)
  .mount('#app')

2. Core Concepts

vuex에서는 Core Concepts가 5개가 있다.

Core Concepts매칭 되는 것
Statedata(반응형)
Getterscomputed(계산된 상태)
Mutationsmethods, state의 데이터 수정 권한
Actionsmethods

이들을 Modules(모듈화)를 별도로 한다.

3. store

3-1. store의 구성

src폴더 안에 store폴더를 만들고 그 안에 index.js 파일을 만들어 사용하자.

import { createStore } from 'vuex'

export default createStore({
  state() {
    count
  },
  getters: {

  },
  mutations: {
	increment(state) {
      state.count++
    }
  },
  actions: {
	increment(context) {
      commit('increment')
  })

ex) 호출 시

store.commit('increment')
store.dispatch('increment')

3-2. Context with Payload

  1. context
    store에있는 함수를 호출할 때 context를 사용하는데 이를 구조 분해를 한다면 다음과 같다.
const { state, getters, commit, dispatch } = context
Core Concepts매칭 되는 것
Statestate
Gettersgetters
Mutationscommit
Actionsdispatch
  1. payload
    매개변수를 넣기 위해 사용하며 payload는 객체 데이터이다.
mutations: {
  increment (state, payload) {
    state.count += payload.amount
  }
}

ex) 호출 시

store.commit('increment', {
  amount: 10
})

3-3. module화 및 등록

store파일에 있는 index.js에서 state(data부분)에 여러 값들이 있고, 이 때문에 메소드들이 복잡해져서 나누고 싶어졌다. 다른 module을 만들고 싶다면 어떻게 할까?

먼저 store내부에 다른 module을 js파일로 만들어주어 모듈화를 한다.
이 module들은 위에 import없이 export default로 작성해주면 된다.

★ 이때 중요한 것은 module화 시킨 파일에 namespaced: true를 꼭 추가해 줘야 한다!

아래의 예시를 보면서 이해해보자!

index.js

import { createStore } from 'vuex'
import module1 from './module1'
import module1 from './module2'

export default createStore({
  modules: {
  	module1,
    module2
  })

각 module들 파일 작성 방법: module1

// module1
export default {
  namespaced: true,
  state() {
    // 관련 데이터
  },
  getters() {
  },
  mutations: {
    // 관련 권한들
  },
  actions: {
    // 관련 메소드
  }
}

각 module들 파일 작성 방법: module2

// module2
export default {
  namespaced: true,
  state() {
    // 관련 데이터
  },
  getters() {
  },
  mutations: {
    // 관련 권한들
  },
  actions: {
    // 관련 메소드
  }
}

4. store에 접근하여 가져오기

store에서 데이터, 함수 등을 가져오는건 간단하다.
this.$store를 이용해서 가져오면 된다!

위에 배운 내용을 토대로 아래의 예시를 보며 이해를 해보자!

import { createStore } from 'vuex'

export default createStore({
  state() {
    return {
      count: 0
    }
  },
  getters: {

  },
  mutations: {
    // 내부에서 사용하는 것을 권장한다!
    // 예시를 위해 actions와 mutations에서 사용을 해본다!
    increase(state) {	
      // state객체를 받는데 이는 위에 있는 state이다.
      // state객체를 매개변수로 받아 접근을 하는 것이다!
      // 수정 권한을 준 것이다!
      state.count += 1
    }
  },
  actions: {
	increase({ commit }) {
      //const { state, getters, commit, dispatch } = context
      commit('increase')
    }
  })
// vue 파일의 script부분
export default {
  computed: {
      data() {
        // store에서 count를 가져옴
        return this.$store.state.count
      }
    },
  	methods: {
      increase() {
        // 1. mutation에서 호출
        // commit: mutations을 호출해 줘라의 메소드! 
		this.$store.commit('increase')
        
        // 2. actions에서 호출
        // dispatch: actions을 호출 해줘라 메소드!
        this.$store.dispatch('increase')
      }
    }
}

★ 여기서 모듈화를 이용했을 때 접근하는 방법을 알아보자!
module화에서 쓴 예시를 예로 들어 보겠다.

export default createStore({
  modules: {
  	module1,
    module2
  })
// module1
export default {
  namespaced: true,
  state() {
    return {
      count: 1
    }
  },
  getters() {
  },
  mutations: {
    increase(state) {	
      state.count += 1
    }
  },
  actions: {
	increase({ commit }) {
      commit('increase')
    }
}
// module2
export default {
  namespaced: true,
  state() {
    return {
      count: 2
    }
  },
  getters() {
  },
   mutations: {
    increase(state) {	
      state.count += 1
    }
  },
  actions: {
	increase({ commit }) {
       commit('increase')
    }
}
// vue 파일의 script부분
export default {
  	methods: {
      increase() {
        // module1 호출!
		this.$store.commit('module1/increase')
        // module2 호출!
        this.$store.dispatch('module2/increase')
      }
    }
}

vue파일에서 가져오려면 바로 위의 예시처럼 modules에 명시한 이름을 앞에 작성해주고 '/'을 작성 후 메소드를 입력하면 해당 module의 메소드를 실행하게 된다!

3. Pinia

vuex에서는 mutations가 데이터 수정 권한을 가지고 있었다.
이 경우 안정적이지만 mutations에 코드를 만드는게 복잡하고 불편하다.

pinia는 불안하지만 mutations처럼 코드로 만들지 않아도 된다.

pinia의 자세한 사항은 아래 링크의 문서를 참고하면 된다.

https://pinia.vuejs.org/core-concepts/

1. 설치

npm install pinia

pinia를 연결하기 위해 main.js에 다음과 같이 코드를 작성 해준다.

// src/main.js
import { createApp } from 'vue'
import App from './App.vue'
import { createPinia } from 'pinia'

createApp(App)
  .use(createPinia())
  .mount('#app')

2. Core Concepts

pinia에서는 State, Getters, Actions 3가지로 줄어들었다.

Core Concepts매칭 되는 것
Statedata
Getterscomputed(계산된 상태)
Actionsstate의 수정 권한

Modules(모듈화)는 기본이다.

3. module화

pinia에서는 vuex와 다르게 module화 할 때, namespaced를 작성할 필요가 없다!

메세지를 반전시키는 간단한 예제로 확인해보자!
주석을 잘 읽어보면 확인해 보면 도움이 될 것이다!

// store파일 안의 module.js
import { defineStore } from 'pinia'

export const useMessageStore = defineStore({
  state: () => ({
    // data
    message: 'Hello world!'
  }),
  getters: {
    // 계산된 데이터(computed data)
    reversedMessage(state) {
      return state.message.split('').reverse().join('')
    }
  },
  actions: {
    reverseMessage() {
      // vuex에서는 context를 통하여 접근했지만 pinia에선 this로 접근한다!
      this.message = this.message.split('').reverse().join('')
    }
  }
})
// vue 파일의 script부분
import { mapState } from 'pinia'
import { useMessageStore } from './store/message'

export default {
  computed: {
  	...mapState(useMessageStore, [
    	'message'  
    ])
  }
}
profile
잘 할 수 있는 개발자가 되기 위하여

0개의 댓글