新しいVue 3アプリケーションの初期化コードのメリット
6381 ワード
この記事では、まず、Vue 2アプリケーションのアプリケーション初期化コードがどのように動作しているかを見てみましょう.次に、どのような欠点があるのか、Vueフレームワークの第3版で使用されている新しい初期化構文を通じてこれらの欠点を解消する方法を見ることができます.
まず,現在のVue 2における初期化方式について述べる.通常、
このアプリケーション・インスタンスは、SPAのライフサイクル全体ですべての論理サービスを提供します.これらはすべてよくて、約3年来、私たちはずっとこの文法を使って私たちのVueアプリケーションを導いています.
ただし、Vue 3では、初期化コード構文が変更されています.まず新しい文法を見て、それを使うメリットを見てみましょう.
新しいVue 3 createAppメソッド
Vue 3では,これを実現するために専門的な
createAppが返すVueアプリケーションインスタンスは、アプリケーションコンテキストオブジェクトとも呼ばれます.このオブジェクトは、ブート中にアプリケーションにさらに多くの機能を追加するために使用できます.以下に、より高度な初期化コードの例を示します.
V 2と比較して、プラグインやコンポーネントなどの追加論理には大きな変化はありませんよね?
サポートされているメソッドの概要は、Vue 3ドキュメントに記載されています.
これはいいですが、
では、なぜ新しい専用
Vue 3初期化コードのメリット
Vue 2アプリケーション初期化コードでは、ライブラリからインポートしたVueオブジェクトを使用して、このアプリケーションインスタンスおよび他のすべての新しいアプリケーションインスタンスを作成します.
この方法では、Vueアプリケーションがライブラリからインポートした同じVueオブジェクトを使用しているため、一部の機能を1つのVueインスタンスにのみ分離することはできません.
この点を示すために、
1つのWebサイトまたはアプリケーションで複数のVueアプリケーションを作成するのは一般的ではありません.
しかし、プロジェクトの規模が拡大するにつれて、異なるチームが開発し、フロントのマイクロサービスが流行し、いつか自分もそうしていることに気づくかもしれません.
その後、v 2構文を使用して別の異なる機能を有するVueインスタンスを得ることはほとんど不可能である.
Vue 3の新しい構文では、アプリケーションが個別のインスタンスを作成するために専用関数(
新しいアーキテクチャにより、2つ以上の孤立したVueインスタンスを持つことができます.デフォルトでは、1つのファイルで作成された場合でも、プロパティは共有されません.
しかし、2つのインスタンスの間でいくつかの機能を共有したい場合は、できます.次の例では、
この挙動を実証するために,2つの簡単なVue 3インスタンスを用いて,新しい
セットの倉庫では、public/index.htmlを参照して、1つのページテンプレートの2つの異なるコンテナで2つのVue 3アプリケーションを初期化しました.
より直接的なテスト設定
私たちのテストシーンでは、Vue 2アプリケーションと同じ潜在的な問題があります.コンポーネント、プラグインなどを追加すると、グローバルVueインスタンスが汚染され、使用可能なVueインスタンスごとに共有されます.
この問題を解決するには、
これは、プラグイン、mixins、およびグローバルコンポーネントがグローバルVueインスタンスを変更しないため、Vue 3では問題ではありません.したがって、Vue 3で
まず,現在のVue 2における初期化方式について述べる.通常、
src/main.js
ファイルでは、アプリケーションインスタンスを作成するコンストラクション関数として新しいVueを呼び出すことによってアプリケーションを起動します.import Vue from "vue";
import App from "./App.vue";
import router from './router'
import SomeComponent from '@/components/SomeComponent.vue'
import SomePlugin from '@/plugins/SomePlugin'
const vue2AppCopy = new Vue({
router,
render: h => h(App)
});
vue2AppCopy.component('SomeComponent',SomeComponent);
vue2AppCopy.use(SomePlugin);
vue2AppCopy.$mount('#app')
このアプリケーション・インスタンスは、SPAのライフサイクル全体ですべての論理サービスを提供します.これらはすべてよくて、約3年来、私たちはずっとこの文法を使って私たちのVueアプリケーションを導いています.
ただし、Vue 3では、初期化コード構文が変更されています.まず新しい文法を見て、それを使うメリットを見てみましょう.
新しいVue 3 createAppメソッド
Vue 3では,これを実現するために専門的な
createApp
関数がある.createApp関数は、パラメータとしてルートコンポーネント(App.vue
)を使用し、Vue適用インスタンスを返します.したがって、最も簡単なアプリケーションの初期化は以下のようになります.import { createApp } from 'vue'
import App from './App.vue'
createApp(App).mount('#app')
createAppが返すVueアプリケーションインスタンスは、アプリケーションコンテキストオブジェクトとも呼ばれます.このオブジェクトは、ブート中にアプリケーションにさらに多くの機能を追加するために使用できます.以下に、より高度な初期化コードの例を示します.
import { createApp } from 'vue'
import App from './App.vue'
import router from './router'
import SomeComponent from '@/components/SomeComponent.vue'
import SomePlugin from '@/plugins/SomePlugin'
const myV3App = createApp(App)
myV3App.component('SomeComponent', SomeComponent)
myV3App
.use(SomePlugin)
.use(router)
// add more functionality to myV3App
// now we're ready to mount
myV3App.mount('#app')
V 2と比較して、プラグインやコンポーネントなどの追加論理には大きな変化はありませんよね?
サポートされているメソッドの概要は、Vue 3ドキュメントに記載されています.
これはいいですが、
new Vue
の例ではなく、専門的な関数を使用しています.//v2
const vue2App = new Vue({}) // Working with the main Vue instace
//v3
const myV3App = createApp(App).mount('#app') // Create a copy of the Vue instance
では、なぜ新しい専用
createApp
関数を使用するのがnew Vue
構造関数を使用するより良いのでしょうか.Vue 3初期化コードのメリット
Vue 2アプリケーション初期化コードでは、ライブラリからインポートしたVueオブジェクトを使用して、このアプリケーションインスタンスおよび他のすべての新しいアプリケーションインスタンスを作成します.
この方法では、Vueアプリケーションがライブラリからインポートした同じVueオブジェクトを使用しているため、一部の機能を1つのVueインスタンスにのみ分離することはできません.
この点を示すために、
vue2AppOne
とvue2AppTwo
の両方がmyDirective
というコマンドにアクセスできる例を見てみましょう.Vue.directive('myDirective', {
/* ... */
})
Vue.component({
/* ... */
})
const vue2AppOne = new Vue(/**/).mount('#app1')
const vue2AppTwo = new Vue(/**/).mount('#app1')
1つのWebサイトまたはアプリケーションで複数のVueアプリケーションを作成するのは一般的ではありません.
しかし、プロジェクトの規模が拡大するにつれて、異なるチームが開発し、フロントのマイクロサービスが流行し、いつか自分もそうしていることに気づくかもしれません.
その後、v 2構文を使用して別の異なる機能を有するVueインスタンスを得ることはほとんど不可能である.
Vue 3の新しい構文では、アプリケーションが個別のインスタンスを作成するために専用関数(
createApp
)を使用するため、各アプリケーションの構成を個別のカスタムオブジェクトとして使用できます.新しいアーキテクチャにより、2つ以上の孤立したVueインスタンスを持つことができます.デフォルトでは、1つのファイルで作成された場合でも、プロパティは共有されません.
しかし、2つのインスタンスの間でいくつかの機能を共有したい場合は、できます.次の例では、
vue3AppOne
およびvue3AppTwo
はLocalePlugin
を共有するが、searchchinputcomponent
は共有しない.const config = {/* some global config */}
const vue3AppOne = Vue.createApp(config)
vue3AppOne.component('SearchInput', SearchInputComponent)
vue3AppOne.use(LocalePlugin)
const vue3AppTwo = Vue.createApp(config)
vue3AppTwo.use(LocalePlugin)
この挙動を実証するために,2つの簡単なVue 3インスタンスを用いて,新しい
createApp
シンタックスが使用されるため,これらのインスタンスはコンポーネントと命令を共有しないコードウェアハウスを作成した.地元での遊び方を見てください.セットの倉庫では、public/index.htmlを参照して、1つのページテンプレートの2つの異なるコンテナで2つのVue 3アプリケーションを初期化しました.
一个应用程序将作为一个相对简单的header标记,而另一个将能够使用router并与store合作。
使用Vue 3语法,我们可以轻松地在src/main.js文件的初始化代码中将它们分开:
import { createApp } from 'vue'
import App from './App.vue'
import Header from './Header.vue'
import router from './router'
import store from './store'
createApp(App)
.use(store)
.use(router)
.mount('#main-app')
createApp(Header)
.mount('#header-app')
vue serve
を使用してアプリケーションを実行すると、2つの部分が1つのページで動作していることがわかります.コンソール出力では、MainアプリケーションはVuex
を使用してvue-router
とショップにアクセスできますが、Headerアプリケーションはできません.created () {
console.log('Hello from Main app')
console.log('Main app router', this.$route)
console.log('Main app store:', this.$store)
}
より直接的なテスト設定
vue-test-utils
(バージョン<2.0.0)を使用してVue 2コンポーネントのテストを作成している場合は、createLocalVue
メソッドを使用してグローバルVueインスタンスを汚染しないようにする必要がある場合があります.私たちのテストシーンでは、Vue 2アプリケーションと同じ潜在的な問題があります.コンポーネント、プラグインなどを追加すると、グローバルVueインスタンスが汚染され、使用可能なVueインスタンスごとに共有されます.
この問題を解決するには、
createlocalvalue
を使用して、新しい孤立したローカルVueインスタンスを作成する必要があります.import { createLocalVue, mount } from '@vue/test-utils'
import MyPlugin from '@/plugins/MyPlugin'
const localVueForTest = createLocalVue()
localVueForTest.use(MyPlugin)
mount(Component, {
localVueForTest
})
これは、プラグイン、mixins、およびグローバルコンポーネントがグローバルVueインスタンスを変更しないため、Vue 3では問題ではありません.したがって、Vue 3で
vue-test-utils
(バージョン>=2.0.0)を使用すると、テストファイルのアプリケーション初期化コードは次のようになります.import { createStore } from 'vuex'
import { mount } from '@vue/test-utils'
import App from '@/App'
import MyPlugin from '@/plugins/MyPlugin'
const wrapper = mount(App, {
global: {
plugins: [MyPlugin]
}
})