Posted at

Vue.js の単一ファイルコンポーネントをプラグインとして作る

More than 1 year has passed since last update.

めもです。

Vue.js のコンポーネントをプラグインとして開発するための、情報と方法の簡単なまとめです。


tl;dr


app.html

<div id="app">

<MyComponent />
</div>


app.js

import Vue from 'vue'

import MyComponent from './my-component.vue'

MyComponent.install = function ( VueConstructor ){
VueConstructor.component( MyComponent.name, MyComponent )
}

Vue.use( MyComponent ) // `MyComponent.install()` が実行される。

new Vue({ el: '#app' })



触れないこと


  • Vue.js と単一ファイルコンポーネントの使い方、作り方

  • JSX, Babel


Vue.js のプラグイン機能


プラグイン — Vue.js https://jp.vuejs.org/v2/guide/plugins.html


Vue.js にはプラグイン機能があり、 ElementUI や Vuetify などのコンポーネントライブラリはこの機構を利用して提供されます。

もちろん公式で提供されている vuexvue-router のようなプラグインも同様です。


プラグインの使用方法、仕組み


使用方法

Vue.js のプラグインをアプリケーション内で利用するには、 Vue.use() メソッドを使用します。

第一引数にプラグインのオブジェクト(又は関数)を渡します。


Vuexの場合

import Vue from 'vue'

import Vuex from 'vuex'

Vue.use( Vuex )


プラグインにオプションが存在する場合は、第二引数にそのオプションを渡してあげます。


ElementUIの場合

import Vue from 'vue'

import Element from 'element-ui'
import locale from 'element-ui/lib/locale/lang/ja'

Vue.use( Element, { locale } )



仕組み

さて、この Vue.js のプラグイン機構ですが、

肝心な部分として、プラグインのオブジェクトをプラグインとして機能させるには

install() というメソッドを定義してあげる必要があります。

MyPlugin.install = function ( Vue, option ) {

// foobar
}

このメソッドの第一引数には Vue コンストラクタを取り、第二引数 (option) では use() の第二引数に渡した値を受け取ります。

option は上の ElementUI の例で言う所の { locale } が該当します。

Vue.use() に何らかのオブジェクトを渡すと install() の実行が試みられるので、この install() 内でプラグインの初期化処理を行うという訳です。

なお Vue.use() の第一引数に対して Object ではなく関数が渡されると、関数自体をインストーラーと見做して実行するようです。…まだ試したことは無いです。

(参照: https://github.com/vuejs/vue/blob/dev/src/core/global-api/use.js#L17


プラグインとしてのコンポーネント

Vue.js プラグインの仕組みが分かったので、コンポーネントライブラリのように Vue.use() して利用するコンポーネントの作り方です。

特に難しいことは無くて、例に倣ってコンポーネントに対して install() メソッドを実装してあげるだけです。

以下で紹介するのは、次の両方での利用が可能なプラグインのコードのイメージです。



  • Vue.use() でグローバルコンポーネントとして登録して利用する。

  • グローバルに登録せず、 インスタンス毎で利用する。


my-component.vue

<template>

<div class="my-component">
foobar
</div>
</template>

<script>
export default {
name: 'MyComponent',
mounted () {
this.$nextTick(() => {
alert( 'mounted!!' )
})
}
}
</script>



installer.js

import MyComponent from './my-component.vue'

MyComponent.install = function (Vue) {
Vue.component( MyComponent.name, MyComponent )
}

export default MyComponent



app.js

import Vue from 'vue'

import MyComponent from './installer.js'

Vue.use( MyComponent )

// または

new Vue({
el: '#app',
components: {
MyComponent
}
})


こんな感じになります。


外部に公開したり複数プロジェクトで使い回す予定がなくても、

プラグインという形式でまとまった機能を作り、アプリケーション全体で共通して利用するというのも良さそうですね。