6
5

More than 5 years have passed since last update.

算出プロパティなAtomコンポーネントを自動テストしてみよう

Last updated at Posted at 2019-09-05

はじめに

Vue.jsを使うのもなんか慣れてきたし、AtomicDesignに基づいたComponentも作れるようになってきたな…
せや!そろそろ自動テストやってみるか!
てなことで、AtomなComponentを自動テストしてみた記事です。

AtomicDesignとは

Javascriptのコンポーネント指向なフレームワークをどう設計していくかの設計思想です。
コンポーネントを5つの構造に分け、それぞれの役割を明確に決め、再利用や可読性を上げます。

  • Atom
  • Molecules
  • Organisms
  • Templates
  • Pages

Atomが最小のコンポーネントとなり、下にいくほど規模が大きくなっていくイメージです。
(#AtomicDesignについては、Qiita含めたくさん記事があるので詳しくは省略します)

今回は、その中でAtomを対象にしたいと思います!

テスト環境

  • Vue.js
  • vue-test-utils
  • Jest

vue-cliのプロジェクト作成時に、Manualを選びTestを有効化し今回はJestを選択しました。

やってみよう

ということで、ぱぱっと以下のようなComponentをテスト自動してみましょう

AtomInput.vue
<template>
    <input 
        type="text" 
        v-model="inputText"
    >
</template>

<script>
export default {
    name:"Atom-input",
    props:{
        value:{
            type:[String, Number]
        }
    },
    computed:{
        inputText:{
            get:function(){
                return this.value
            },
            set:function(value){
                this.$emit("change",value)
            }
        }
    }
}
</script>

Atomのルールとして、状態やデータを持ってはならないというのがあるため、dataの記述がないコンポーネントとなります。
上位からpropsvalueの値を受け取り、それをcomputedsetter/getterを経由しv-modelでinputに紐づけております。
propsをそのままv-modelinputにバインディングしたいところですが、Vueのルールとして単方向データフローがあります。
propsを子コンポーネントが変更することはそのルールに違反することとなりますので、子から直接propsの値を変更することはできません。
そこで、computedsetter/getterを使うことで、v-modelが値を呼び出すときはgetterpropsの値を取得、変更はsetterで親への通知イベントを行っています。

参考にさせていただいた記事

テストを作ってみよう

1つのコンポーネントで行うべきテストケースは色々ありますが、今回は1つに絞ります。
テストケースとしては、
入力した値が親に返されてくるかをテストしてみたいと思います。

AtomInput.spec.js
describe('AtomInputText.vue',()=>{
    it('入力した値が親に返されてくるか',()=>{
        const wrapper = mount(Input);
        const value = 'valueだよ';
        const input = wrapper.find('input[type="text"]');
        input.setValue(value)//v-model on change
        expect(wrapper.emitted().change[0][0]).toBe(value);
    });
});

内容としてはとてもシンプルです。
対象コンポーネント内にあるinputを見つけて、それに対してsetValueで値をセットしています。
setValue自体が、セットとinputイベントを同時に行うAPI的な書き方ですので、1行で済ますことができます
Vue Test Utils : setValue

setValueを使わずに書くとしたら、

   input.setValue(value)//v-model on change

これが

   input.element.value = value
   input.trigger('input')

こういう風な書き方となります。

setValueinputが行われるため、v-model="inputText"のから算出プロパティのsetterが呼び出されます。
そしてsetterには$emitがあるため、引数の値を親にイベントで伝えております。
なのでテストコード側では最後にemittedでやってきた値を見ることで、
正しく入力された値がやってくるかのチェックができます。

上の方にも書きましたが、再利用性を高めるためにAtomやMoleculesでは状態を持ってはいけないため、
テストコード側でも入力した値をテストするために、dataなどを確認するのではなくemittedで確認しています。

やってみた感想

書いてみるとすごく短くて記事としてもシンプルなものとなりましたが、知らずにやろうとしたら割と詰まったので記事にしてみました。
テストケースを書くことで、データの流れやイベントなどをより意識しコーディングするようになったので、テスト自動化は早めに着手するのがいいなと感じました。

6
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
6
5