7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

TypeScriptのPropsでProperty '...' does not exist on type 'Vue'エラー

Posted at

Nuxt×TSの環境で、Vue.extend()を使っていますが、いつもどおりPropsの型定義をしていたらProperty '...' does not exist on type 'Vue'のエラーが出ました。
初見のパターンだったのでメモ。

ドロップダウンのコンポーネントですが、propsでdropdownStylesオブジェクトを受け取っている部分だけ見てもらえばOKです。

エラーが出る書き方


<template>
  <div class="dropdown">
    <div @click="openModal"></div>
    <modal
      :name="dropdownStyles.name"
      class="modal"
    >
    </modal>
  </div>
</template>

<script lang="ts">
import Vue from 'vue';

//Propsの型定義
type DropdownStyles = {
  name: string;
};

export default Vue.extend({
  name: 'AppDropdown',
  props: {
    dropdownStyles: {
      //propsの型を指定できてると思ったら...
      type: Object as Vue.PropType<DropdownStyles>,
        defalt: () => ({
          name: 'dropdown'
        }),
      required: true
    }
  },
  methods: {
    openModal(): void {
      this.$modal.show(this.dropdownStyles.name);
    }
  }
});
</script>

propsのtypeで型定義をしているから大丈夫だろう...と思っていたらここでビルドエラーが出ました。

エラー内容


46:29 Property 'dropdownStyles' does not exist on type 'Vue'.
 
    44 |   methods: {
    45 |     openModal() { 
  > 46 |       this.$modal.show(this.dropdownStyles.name);
       |                             ^
    47 |     }
    48 |   }
    49 | });
 

ええ...型定義したじゃん...😭

と思いましたが、Vueのoptionsの型定義も必要だったようです。

参考: TypeScript の Vue.extend(options) で options の型を明示せず data などの同時指定時に props の default がアロー関数でないと型の解釈ができなくなる

defaultをアロー関数で指定していたので、上記の記事のパターンとは微妙に違うのですが参考になりました。

エラーが出ない書き方


<template>
  <div class="dropdown">
    <div @click="openModal"></div>
    <modal
      :name="dropdownStyles.name"
      class="modal"
    >
    </modal>
  </div>
</template>

<script lang="ts">
import Vue from 'vue';

type DropdownStyles = {
  name: string;
};

//ここでPropsとMethodsの型を定義
//computedとdataは無いので書いてません
type Props = {
  dropdownStyles: DropdownStyles;
};

type Methods = {
  openModal: () => void;
};

//ここでVue.extendに渡されるoptionsの型を指定
//コンポーネントに存在しないオプションの部分は空のオブジェクトを指定
export default Vue.extend<{}, Methods, {}, Props>({
  name: 'AppDropdown',
  props: {
    dropdownStyles: {
      type: Object as Vue.PropType<DropdownStyles>,
        defalt: () => ({
          name: 'dropdown'
        }),
      required: true
    }
  },
  methods: {
    openModal(): void {
      this.$modal.show(this.dropdownStyles.name);
    }
  }
});
</script>
7
5
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?