RyoGIFT | Web developer blog

Web開発者のブログです。

Vue.jsで簡単なテストを書いてみる

Vue.jsによって、生成されたDOMの結果を確認する。

<!-- src/components/Sample.vue -->
<template>
  <div class="sample">
    <p>sample</p>
  </div>
</template>

<script>
export default {
  name: "Sample"
}
</script>

<style scoped>
.sample {
  text-align: center;
}
</style>
// tests/unit/components/Sample.spec.js
import { shallowMount } from "@vue/test-utils"
import Sample from "@/components/Sample.vue"

describe("Sample.vue", () => {
  it("sampleの文字列が描画されること", () => {
    const wrapper = shallowMount(Sample)
    expect(wrapper.text()).toMatch("sample")
  })
})
$ npm run test:unit                 
> vue-cli-service test:unit

 PASS  tests/unit/components/Sample.spec.js
  Sample.vue
    ✓ sampleの文字列が描画されること (25ms)

Test Suites: 1 passed, 1 total
Tests:       1 passed, 1 total
Snapshots:   0 total
Time:        3.457s
Ran all test suites.

Reactで簡単なテストを書いてみる

Reactによって、生成されたDOMの結果を確認する。

/* App.css */
.App {
  text-align: center;
}
// App.js
import "./App.css";

const App = () => (
  <div className="App">
    <p>sample</p>
  </div>
);

export default App;
// App.test.js
import { render, screen } from "@testing-library/react";
import App from "./App";

test("sampleの文字列が描画されること", () => {
  render(<App />);
  const textElement = screen.getByText("sample");
  expect(textElement).toBeInTheDocument();
});
$ yarn test ./src/App.test.js
 PASS  src/App.test.js
  ✓ sampleの文字列が描画されること (61 ms)

Test Suites: 1 passed, 1 total
Tests:       1 passed, 1 total
Snapshots:   0 total
Time:        5.023 s, estimated 7 s

Ubuntu 20.04.1 LTSにPostgreSQLをインストール

パッケージリストの追加で"bionic-pgdg"ではエラーになったため、インストール方法を記載します。

手順

あらかじめ root ユーザに切り替えておく。

  1. PostgreSQLのダウンロードURLをパッケージリストに追加する。
  2. PostgreSQLの公開鍵をキーリストに追加する。
  3. パッケージ内容を更新する。
  4. PostgreSQLをインストールする。
$ echo "deb http://apt.postgresql.org/pub/repos/apt/ focal-pgdg main" | tee /etc/apt/sources.list.d/pgdg.list
$ curl -sS http://apt.postgresql.org/pub/repos/apt/ACCC4CF8.asc | apt-key add -
$ apt update
$ apt install postgresql

PostgreSQL 13 がインストールできました。

$ psql --version
psql (PostgreSQL) 13.0 (Ubuntu 13.0-1.pgdg20.04+1)

ダック・タイピングを例に動的型付け言語と静的型付け言語の違い

ダック・タイピングとは
If it walks like a duck and quacks like a duck, it must be a duck.  
(もしも、それがアヒルのように歩き、アヒルのように鳴くのなら、それはアヒルに違いない。)  
                                デーブ・トーマスより

ダック・タイピングは、オブジェクトに何ができるかはオブジェクトそのものが決定します。静的型付け言語と違って継承関係が無く、オブジェクトがインタフェースのすべてのメソッドを持っている場合には、対象のクラスがインタフェースを宣言的に実装していない場合でもオブジェクトを呼び出すことができます。

Rubyを使ったコード例
class Duck
  def sound
    "Quack"
  end
end

class Cat
  def sound
    "Meow"
  end
end

def sound(object)
  object.sound
end

puts sound(Duck.new)
puts sound(Cat.new)

soundメソッドはオブジェクトにsoundメソッドが定義されているのかを確認できませんが実行時には呼び出すことが出来ます。

Javaでインタフェースを使って、同様の出力結果になるコード例
// Animal.java
package com.ry0takahash1;

public interface Animal {
    public abstract String sound();
}

// Duck.java
package com.ry0takahash1;

public class Duck implements Animal {
    public String sound() {
        return "Quack";
    }
}

// Cat.java
package com.ry0takahash1;

public class Cat implements Animal {
    public String sound() {
        return "Meow";
    }
}

// Main.java
package com.ry0takahash1;

public class Main {
    public static void main(String[] args) {
        Duck duck = new Duck();
        System.out.println(duck.sound());

        Cat cat = new Cat();
        System.out.println(cat.sound());
    }
}

インタフェースで、あらかじめメソッドを宣言しているため実行しなくてもsoundメソッドが定義されていることが明示的に分かります。

まとめ

ダック・タイピングを例に動的型付け言語と静的型付け言語の違いを考えてみました。個人的には個人開発や小規模なチームでの開発であれば動的型付け言語、大規模なチームでの開発であれば静的型付け言語を使うかなと思います。適材適所でプログラミング言語の使い分けが出来ると良いですね!

ES6とReactとVue.jsの基礎を学ぶ

JavaScriptの勉強

最近、JavaScriptを中心に勉強しています。業務ではVue.jsを使っていますが、Reactにも興味があり少しずつコードを書き始めました。ReactはSimple、Vue.jsはEasyと言われておりますが、その意味も理解できるようになってきました。私は下記のサイトを参考に勉強をしました。

順番的にはJavaScript PrimerでES6を学んでからReactのチュートリアルをやってみるとパターンが似ており、分かりやすいと思います。

コードの比較

ES6では以下のような書き方がベースになります。(処理の中身は省略しています。)

export class App {
  constructor() {
  }

  handleAdd(title) {
  }

  handleUpdate({ id, completed }) {
  }

  handleDelete({ id }) {
  }

  handleSubmit(event) {
  }

  handleChange() {
  }

  mount() {
  }

  unmount () {
  }
}

Reactは、このような書き方です。ES6での書き方と似ています。(処理の中身は省略しています。)

class Game extends React.Component {
  constructor(props) {
    super(props);
    this.state = {};
  }

  handleClick(i) {
  }

  render() {
    const history = this.state.history;
    return (
      <div className="game">
      </div>
    );
  }
}

また、DOMを返すだけの場合はAllow Functionベースで書くこともできます。

const Square = (props) => (
  <button className="square" onClick={props.onClick}>
    {props.value}
  </button>
);

そして、Vue.jsでは単一ファイルコンポーネントで書きます。(処理の中身は省略しています。)

<template>
</template>

<script>
export default {
  data () {
    return {
    }
  },
  methods: {
  }
};
</script>

<style scoped>
</style>

ES6やReactはオブジェクト指向のクラスという仕組みに近いですが、Vue.jsはメソッドを多く定義していくようなイメージです。どの書き方が良いかは好みの問題かと思いますが、個人的にはReactの書き方が好きです。実際に業務で使うとなるとRestAPIを呼び出すために、axiosライブラリを利用したり、GraphQLAPIを呼び出すためにApolloが提供しているライブラリを利用しますが、 複雑さが増していくとVue.jsの単一ファイルコンポーネントの書き方では行数が増えてしまい、少し見づらくなってきます。SPAを本格的に実装するときは、やっぱりReactの方が優れているかなと最近、感じています。

余談

しかし、フロントエンドの領域も様々な仕組みやベストプラクティスが蓄積されてきており、難しくなってきたなと感じています。 数年前までは控えめなJavaScriptが主流でしたし、少しjQueryとかが書けるだけで一般的なシステムの開発が出来ていました。技術の進歩は嬉しいですが、追いつくのもひと苦労ですね。