🛡️ 3-3. 型安全な Vuex との連携(TypeScript 使用時)

✅ 要点まとめ


🟢 基本の型定義(具体例)

1️⃣ State の型を定義

// ファイル名: store/state.ts
export interface State {
  count: number;
}


2️⃣ Store の作成(型付き)

// ファイル名: store/index.ts
import { createStore } from 'vuex';
import { State } from './state';

export const store = createStore<State>({
  state: {
    count: 0,
  },
  getters: {
    doubleCount: (state) => state.count * 2,
  },
  mutations: {
    setCount(state, payload: number) {
      state.count = payload;
    },
  },
  actions: {
    increment({ commit }) {
      commit('setCount', 1);
    },
  },
});

// Store の型をエクスポート
export type StoreType = typeof store;


3️⃣ 型付きの useStore() を作る

// ファイル名: store/useStore.ts
import { useStore as baseUseStore } from 'vuex';
import { store, StoreType } from './index';
import { Store } from 'vuex';

// Store の型を Store<state> にする
export function useStore(): Store<StoreType['state']> {
  return baseUseStore();
}


🟡 コンポーネント側の使用例

<!-- ファイル名: Counter.vue -->
<template>
  <div>
    <p>{{ count }}</p>
    <p>{{ doubleCount }}</p>
    <button @click="increment">+1</button>
  </div>
</template>

<script setup lang="ts">
// 型付き useStore をインポート
import { useStore } from '../store/useStore';
import { computed } from 'vue';

const store = useStore();

// 型推論が効く → 補完される
const count = computed(() => store.state.count);
const doubleCount = computed(() => store.getters.doubleCount);

const increment = () => {
  store.dispatch('increment');
};
</script>