programing

VueJs의 개체에 새 속성을 추가할 때 변경을 트리거하는 방법

javaba 2022. 8. 8. 17:38
반응형

VueJs의 개체에 새 속성을 추가할 때 변경을 트리거하는 방법

(VueJS 프로젝트에서) 다음과 같은 초기 vuex 상태의 구조를 가지고 있습니다.

state: {
    level1prop: null
}

다음으로 동적으로 변경하여 다음과 같은 구조로 변환합니다.

state: {
    level1prop: {
        level2prop: {
            level3prop: {
                "customKey1": { /* this is some object 1 */ },
                "customKey2": { /* this is some object 2 */ },
                ...
            }
        }
    }
}

그때나는 추가될 것이다 때 그를 추가할 것이다."customKeyN": { /* this is some object N */ }그 아래쪽에에level3prop그리고 그것이 중요한 저를 변화는 변화들에 대한 그리고 나에게 중요한 것은 모든 변화에 대해 감시자를 촉발시키는 것이다에를 보고 있는 관측통을 유발할 예정이다.감시자는 그 변화를감시하고 있다.level1prop주.주정부로부터.

처음에 저는 다음과 같은 방법으로 이 업데이트를 하고 있었습니다.

if (!state.hasOwnProperty("level1prop"))
    state["level1prop"] = {};
else if (state["level1prop"] === null || state["level1prop"] === undefined)
    state["level1prop"] = {};

if (!state["level1prop"].hasOwnProperty("level2prop"))
    state["level1prop"]["level2prop"] = {};
else if (state["level1prop"]["level2prop"] === null || state["level1prop"]["level2prop"] === undefined)
    state["level1prop"]["level2prop"] = {};

if (!state["level1prop"]["level2prop"].hasOwnProperty("level3prop"))
    state["level1prop"]["level2prop"]["level3prop"] = {};
else if (state["level1prop"]["level2prop"]["level3prop"] === null || state["level1prop"]["level2prop"]["level3prop"] === undefined)
    state["level1prop"]["level2prop"]["level3prop"] = {};

let payloadObj = {  "customKey1": { /* this is some object 1 */ }  };
state["level1prop"]["level2prop"]["level3prop"] = payloadObj;

그리고 이것은 내가 원하는 방식으로 구조를 만들고 있지만, 변화의 관찰자는 트리거되지 않습니다.여기서의 조언에 따라 코드를 몇 가지 다른 방법으로 수정하지만, 그 중 어느 것도 변경을 유발하지 않습니다.다음은 제가 시도한 최신 옵션의 예입니다.

if (!state.hasOwnProperty("level1prop"))
    state = Object.assign(state, { "level1prop" : {} });
else if (state["level1prop"] === null || state["level1prop"] === undefined)
    state = Object.assign(state, { "level1prop" : {} });

if (!state["level1prop"].hasOwnProperty("level2prop"))
    state["level1prop"] = Object.assign(state["level1prop"], { "level2prop" : {} });
else if (state["level1prop"]["level2prop"] === null || state["level1prop"]["level2prop"] === undefined)
    state["level1prop"] = Object.assign(state["level1prop"], { "level2prop" : {} });

if (!state["level1prop"]["level2prop"].hasOwnProperty("level3prop"))
    state["level1prop"]["level2prop"] = Object.assign(state["level1prop"]["level2prop"], { "level3prop" : {} });
else if (state["level1prop"]["level2prop"]["level3prop"] === null || state["level1prop"]["level2prop"]["level3prop"] === undefined)
    state["level1prop"]["level2prop"] = Object.assign(state["level1prop"]["level2prop"], { "level3prop" : {} });

let payloadObj = {  "customKey 1": { /* this is some object 1 */ }  };
state["level1prop"]["level2prop"]["level3prop"] = Object.assign(state["level1prop"]["level2prop"]["level3prop"], payloadObj);

다시 말씀드리지만, 이것은 제가 필요로 하는 구조를 만들고 있지만, 워처는 아직 트리거되지 않았습니다.그 밖에도 몇 가지 옵션을 시도했지만 변경을 일으키지 않았습니다.

...
state["level1prop"]["level2prop"]["level3prop"] = Object.assign({}, state["level1prop"]["level2prop"]["level3prop"], payloadObj);
...

그리고.

...
Object.assign(state["level1prop"]["level2prop"]["level3prop"], payloadObj);
...

이렇게 복잡한 객체 상태에서 다수의 중첩된 레벨이 있는 워처를 변경할 수 있는 방법이 있습니까?

docs의 "Object Change Detection Warnats" 섹션에서 설명한 바와 같이 특별히 설계된 Vue setter를 사용하여 나중에 서브레벨을 상태에 추가해야 합니다.

그런 다음 하위 수준이 변경될 때 올바르게 트리거되도록 워처가 옵션을 지정했는지 확인하십시오.

const store = new Vuex.Store({
  state: {
    level1prop: null,
  },
});

const state = store.state;

if (!state["level1prop"])
  Vue.set(state, "level1prop", {})

if (!state["level1prop"]["level2prop"])
  Vue.set(state["level1prop"], "level2prop", {})

if (!state["level1prop"]["level2prop"]["level3prop"])
  Vue.set(state["level1prop"]["level2prop"], "level3prop", {})

let payloadObj = {
  "customKey1": {
    hello: "world",
  },
};
state["level1prop"]["level2prop"]["level3prop"] = payloadObj;

setTimeout(() => {
  // Change an already existing key.
  state["level1prop"]["level2prop"]["level3prop"].customKey1.hello = "too";
}, 1000);

setTimeout(() => {
  // To add or remove keys, make sure to use again Vue.set or Vue.delete.
  state["level1prop"]["level2prop"]["level3prop"].customKey1.hello = "too";
  Vue.set(state["level1prop"]["level2prop"], "level3propSibling", {
    hi: "again",
  });
}, 2000);


new Vue({
  store: store,
  watch: {
    "$store.state": {
      // Make sure you specify the `deep` option
      deep: true,
      handler() {
        console.log(store.state);
      },
    },
  },
});
<script src="https://unpkg.com/vue@2"></script>
<script src="https://unpkg.com/vuex@3"></script>

언급URL : https://stackoverflow.com/questions/51411566/how-to-trigger-a-change-when-adding-new-property-in-object-in-vuejs

반응형