programing

고유한 vuex 저장소 인스턴스를 사용해야 하는 구성 요소를 재사용하는 방법

luckcodes 2022. 8. 7. 19:03

고유한 vuex 저장소 인스턴스를 사용해야 하는 구성 요소를 재사용하는 방법

스토어에 데이터를 저장하는 재사용 가능한 컴포넌트와 함께 vuex를 사용하는 방법을 찾고 있습니다.문제는 스토어가 각 컴포넌트 인스턴스에 대해 고유해야 한다는 것입니다.

저는 이 문서의 재사용 가능한 모듈이 열쇠라고 생각했는데, 결국 이 목적을 위한 것이 아닌 것 같거나 사용법을 이해하지 못했습니다.

부모 컴포넌트: (프롭 "req-path"를 사용하여 다른 URL을 전달하고 각 FileExplector 컴포넌트가 해당 URL 경로를 사용하여 API에서 데이터를 가져오는 액션을 커밋합니다.)

<template>
  <div class="container">
    <FileExplorer req-path="/folder/subfolder"></FileExplorer>
    <FileExplorer req-path="/anotherfolder"></FileExplorer>
  </div>
</template>

<script>
import { mapState, mapGetters } from "vuex";
import FileExplorer from "@/components/FileExplorer.vue";

export default {
  components: {
    FileExplorer
  }
};
</script>

재사용 가능한 구성 요소:

<template>
 <div class="container">
      <ul v-for="(item, index) in folderIndex" :key="index">
        <li>Results: {{ item.name }}</li>
      </ul>
    </div>
 </div>
</template>

<script>
import { mapState, mapGetters } from "vuex";

export default {
  props: ["reqPath"],
  },
  computed: {
    ...mapState("fileExplorer", ["folderIndex"])
  },
  created() {
    // FETCH DATA FROM API
    this.$store
      .dispatch("fileExplorer/indexingData", {
        reqPath: this.reqPath
      })
      .catch(error => {
        console.log("An error occurred:", error);
        this.errors = error.response.data.data;
      });
  }
};
</script>

store.js는 다른 파일로 구분된 스토어 모듈을 호출합니다.여기서는 fileExplector 모듈만 관심이 있습니다.EDIT : 알기 쉽게 하기 위해 파일을 단순화했지만 다른 상태가 있어 내부에 많은 돌연변이가 있습니다.

import Vue from 'vue'
import Vuex from 'vuex'

// Import modules
import { fileExplorer } from '@/store/modules/fileExplorer'

Vue.use(Vuex)

export default new Vuex.Store({
modules: {
    fileExplorer,
…
  }
})

@/store/modules/fileExplector.js

import ApiService from "@/utils/ApiService"

export const fileExplorer = ({
namespaced: true,

  state: {
    folderIndex: {},
},

  mutations: {
    // Called from action (indexingData) to fetch folder/fil structure from API
    SET_FOLDERS_INDEX(state, data) {
      state.folderIndex = data.indexingData
},

actions: {
    // Fetch data from API using req-path as url 
    indexingData({
      commit
    }, reqPath) {
      return ApiService.indexingData(reqPath)
        .then((response) => {
          commit('SET_FOLDERS_INDEX', response.data);
        })
        .catch((error) => {
          console.log('There was an error:', error.response);
        });
    }
  }
});

각 컴포넌트가 2개의 다른 URL에서 다른 데이터를 표시해야 합니다.대신 2개의 컴포넌트 인스턴스에서 동일한 데이터를 얻을 수 있습니다(단, 놀라운 것은 아닙니다).

그 모든 것을 읽어주신 모든 분들께 감사드립니다!

모듈 재사용이란 동일한 모듈Configuration에서 여러 모듈을 작성하는 경우를 말합니다.


먼저 플레인 오브젝트 대신 모듈 상태를 선언하는 함수를 사용합니다.

플레인 객체를 사용하여 모듈 상태를 선언하면 해당 상태 객체가 참조에 의해 공유되고 변환 시 크로스 스토어/모듈 상태 오염이 발생합니다.

const fileExplorer = {
  state () {
    return {
      folderIndex: {}
    }
  },
  // mutations, actions, getters...
}

그런 다음 새 모듈을 새로 등록할 때마다 동적으로 등록합니다.FileExplorer컴포넌트가 생성되어 컴포넌트가 파기되기 전에 해당 모듈의 등록을 취소합니다.

<template>
 <div class="container">
      <ul v-for="(item, index) in folderIndex" :key="index">
        <li>Results: {{ item.name }}</li>
      </ul>
    </div>
 </div>
</template>

<script>
import { fileExplorer } from "@/store/modules/fileExplorer";
import store from "@/store/index";

var uid = 1

export default {
  props: ["reqPath"],
  data() {
    return {
      namespace: `fileExplorer${uid++}`
    }
  },
  computed: {
    folderIndex() {
      return this.$store.state[this.namespace].folderIndex
    }
  },
  created() {
    // Register the new module dynamically
    store.registerModule(this.namespace, fileExplorer);

    // FETCH DATA FROM API
    this.$store
      .dispatch(`${this.namespace}/indexingData`, {
        reqPath: this.reqPath
      })
      .catch(error => {
        console.log("An error occurred:", error);
        this.errors = error.response.data.data;
      });
  },
  beforeDestroy() {
    // Unregister the dynamically created module
    store.unregisterModule(this.namespace);
  }
};
</script>

스토어 작성 시 선언된 정적 모듈 등록은 더 이상 필요하지 않습니다.

export default new Vuex.Store({
  modules: {
    // fileExplorer, <-- Remove this static module
  }
})

언급URL : https://stackoverflow.com/questions/58719210/how-to-re-use-component-that-should-use-unique-vuex-store-instance