masakiのブログ Written by masaki shibayama

【2022年最新版】vue.jsでの単体テストの方法をフロントエンドエンジニアがわかりやすく解説

Programming WebApp

こんにちは。masakiです。
今回は、vueでの単体テストの書き方について説明します。

目次は以下のとおりです。

目次

  • 使用するライブラリ
  • Jestの基本的な使い方
  • vue-test-utilsの基本的な使い方
  • 参考書籍

それでは解説していきます。

使用するライブラリ

ライブラリには、Jestとvue-test-utilsを用います。
JestはFacebook(現在はMeta)が開発したライブラリで、テスト用のライブラリとしては圧倒的人気を誇ります。vue-test-utilsは、vueのテスト用ライブラリです。vueの単体テストでは、この2つを用いるのが一般的です。インストール方法についてはここでは解説しないので、ドキュメントや書籍などを参考にしてください。

Jestの公式ドキュメントはこちら
vue-test-utilsの公式ドキュメントはこちら

Jestの基本的な使い方

ディレクトリ構成

まずはディレクトリ構成について説明します。
例えば、プロジェクトの中にExample.vueというコンポーネントファイルがあった場合は、以下のようにExample.test.jsという名前のファイルをtestsフォルダの中に作り、そこにテスト用のコードを書いていけばOKです。

■tests
|
|—–Example.test.js

テストファイルを実行するには、ターミナルで以下のコマンドを叩けばOKです。

npm run test:unit Example.test.js

基本的なメソッド

describe()は、テストスイートを記述するためのメソッドです。テストスイートとは、テストコードを束ねる箱のようなものだと思ってもらえればOKです。使い方としては、以下のような感じです。


describe("jest first test", () => {
  test("check 1 + 1", () => {
    expect(1+1).toBe(2)
  }),
  test("check 2 + 2", () => {
    expect(2+2).toBe(4)
  })
})

上記の例では、describe()の第一引数にテストの名前、第二引数に実行する関数を記載しています。
※アロー関数がわからない方は、JavaScriptの書籍などで復習してみてください。

そしてそのdescribe()の中で、さらにtest()を使って1つ1つのテストコードを記載しています。test()の方もdescribe()と同じく、第一引数にテストの名前、第二引数に実行する関数を記載しています。

今回の場合はtest()を2つ使っているので、1つのテストスイートの中にテストコードが2つあるわけですね。
※test()の省略系のメソッドとしてit()というメソッドもありますが、どちらでも一緒です。

そして、以下の

expect(1+1).toBe(2)

の部分では、1+1という演算の結果が、2になるかどうかを判定しています。
例ではどちらも直値を記載していますが、expect()の引数にはコンポーネント内で得られた実際の値を、toBe()の引数には想定される値を記述するのが一般的です。

ちなみに、toBe()のようなメソッドのことをマッチャーと呼び、他には以下のようなものが存在します。

マッチャー 説明
toBeGreaterThan(value) 値がvalueよりも大きいか
toBeGreaterThanOrEqual(value) 値がvalue以上か
toBeLessThan(value) 値がvalueよりも小さいか
toBeLessThanOrEqual(value) 値がvalue以下か

この辺りはドキュメントの方が詳しいので、どんなマッチャーがあるのかについては一度Jestの公式ドキュメントを見てみた方が良さそうです。

vue-test-utilsの基本的な使い方

ここまで読んだ方は、きっと以下のように思うと思います。

コンポーネント内の値を判定する方法はわかった。でも、コンポーネント内のdataやcomputedの値を取得するには結局どうしたら良いの?

ここで出てくるのが、vue-test-utilsです。このライブラリを使うと、vueインスタンスにアクセスができるようになるので、dataやcomputedの値を簡単にとってくることができます。

基本的なメソッド

vue-test-utilsで最も基本となるメソッドが、sharrowMount()です。
sharrowMount()の戻り値はラッパーというオブジェクトで、このオブジェクトはプロパティとしてvueインスタンス持つので、vueインスタンスから簡単にdataやcomputedなどの値を取得できます。

上記だとまだちょっとわかりにくいかもしれないので、具体例を以下に示します。


import { shallowMount } from "@vue/test-utils"
import Example from "src/components/Example.vue"

describe("vue unit test", () => {
  test("", () => {
    const wrapper = shallowMount(Example)
    expecct(wrapper.find("h1").text()).toBe("example")
  })
})

上記だと、

wrapper.find("h1").text()

のような感じで、Example.vueのテンプレートの、h1タグに囲まれたテキストを取得することができます。
このようにして取得した値をマッチャーで検証すればOKです。

ちなみに、mount()というメソッドもありますが、基本的にはsharrowMount()を利用すると考えてOKです。
sharrowMount()は下位のコンポーネントをスタブ化(ダミーとして作ること)しますが、mount()だとそれをしないというだけの違いです。

ちょっと脱線しましたが、上記からもわかるように、vueにおける単体テストの流れは以下になります。

  • コンポーネントをsharrowMount
  • ラッパーから値を取得
  • マッチャーで検証

今回はここまでとなります。
次回はJestでのモック化の方法について解説したいと思います。

参考書籍

これからはじめるVue.js 3実践入門
Webアプリ開発入門: 4.Jest編 Future Coders テキスト