Vue watch 意外调用两次

low*_*nts 9 javascript vue.js vue-cli

udpate #2:这不是错误,这是我自己的错。我BaseComponent通过一种extend()方法以及放入extends: BaseComponent选项来扩展。我以为我需要两者,但extends: BaseComponent在选项中似乎就足够了。
因此,双重“扩展”显然重复了观察者,这导致了我在问题中记录的奇怪行为。

更新:我发现了导致此问题的原因:观察者似乎是重复的,因为它位于BaseComponentComponent我的示例中使用的which扩展的a中。所以export default BaseComponent.extend({ name: 'Component', ...})似乎复制watch对象而不是“合并”它 - 现在有一个在BaseComponent(它最初实现的地方)和一个在Component- 当然两者都对道具更新做出反应。
恕我直言,这似乎是一个错误。


使用vue-cli单文件组件。
我通过一种方法在一个组件中设置了一个道具:

<template>
  <div>
    <other-component :my-object="myObject" />
  </div>
</template>

<script>
  export default (Vue as VueConstructor).extend({
    data() {
      return {
        myObject: null
      }
    },

    methods: {
      actionButtonClicked(action, ID) {
        console.log('actionButtonClicked');

        this.myObject = {
          action: action,
          ID: ID
        }
      }
    }
  });
</script>
Run Code Online (Sandbox Code Playgroud)

然后我正在使用观察者观察另一个组件中的道具 - 但是每次执行该方法时 watch 都会被调用两次。

<script>

  export default (Vue as VueConstructor<Vue>).extend({
    /* ... */
    props: {
      myObject: {
      type: Object,
      default: null
    },

    watch: {
      'myObject.ID'(value, oldValue) {
        console.log('watcher executed');
      }
    }

    /* ... */
  });

</script>
Run Code Online (Sandbox Code Playgroud)

所以在控制台中我得到输出:

actionButtonClicked
watcher executed
watcher executed
Run Code Online (Sandbox Code Playgroud)

.. 每次调用该方法时。

我已经尝试了所有不同的观察者变体 - 例如deep: true+ handler。但这一切都没有改变观察者被调用两次的任何事情。

Dey*_*ong 16

就我而言,我在组件中有“手表”并在页面上使用该组件两次,因此“手表”被注册了两次。

希望它会帮助有同样问题的人。

  • 我不知道为什么有人不喜欢我的评论。这只是分享,以防其他人遇到同样的情况。 (6认同)
  • 实际上这也是我完全相同的问题 (3认同)

low*_*nts 4

BaseComponent我的观察者被复制,因为我以两种方式 扩展了我的观察者:

  • 通过extend()组件本身的方法
  • 通过放入extends: BaseComponent“外部”组件的选项

我认为您需要使用这两段代码来扩展另一个组件,但显然这是错误的,并且可能会导致严重的副作用。