見出し画像

Test Basics | Go日記: 『Learning Go』

Chapter 13. Writing Tests の学習記録。基本編。(応用編はまたいつか。)
Go でユニットテストを書き始めるのに必要そうな基本的な内容を学習した。

 読書メモ: 頭から Chapter 9. Modules, Packages and Imports までとにかく読んでみた。次に Chapter 10. で並行処理の内容に入る。が、基本中の基本をだいたい把握できたと感じられたので、実務で使うコードを少し書いてみてすぐに「あ、Go のテストについてほとんど知らんな…」と気づいた。そういうわけで、Chapter を数個飛ばしてテストについて学習を進めてみる。

Basics

・テストコードのための testing 標準ライブラリが用意されている。

・テストツール go test コマンドが用意されている。

・プロダクトコードと同じ階層、同じパッケージにテスト設置。

これから書籍内で説明されるサンプルコードの完全版はこちら。

Every test is written in a file whose name ends with _test.go. If you are writing tests against foo.go, place your tests in a file named foo_test.go.

すべてのテストは _test.go で終わるファイルに書く。foo.go に対しては foo_test.go 。

Bodner, Jon. Learning Go (p.399). O'Reilly Media. Kindle 版.

テストコードの書き方については実物を見るのが早い。
 ・import "testing"
 ・関数名に接頭辞 Test
 ・*testing.T 型の引数
 ・*testing.T 型の引数のメソッドを関数ボディーで使用

In the file adder/adder.go, we have:

func addNumbers(x, y int) int {
    return x + x
}

The corresponding test is in adder/adder_test.go:

func Test_addNumbers(t *testing.T) {
    result := addNumbers( 2,3)
    if result != 5 {
        t.Error("incorrect result: expected 5, got", result)
    }
}

Bodner, Jon. Learning Go (p.399). O'Reilly Media. Kindle 版.

pwd が adder サブディレクトリの中なら

go test

でテストが走る。

そうではなく、adder の親ディレクトリにいるなら

go test adder

のように指定するか、次のようにしてテストコードを丸っと実行する。

go test ./...

Reporting Test Failures

*testing.T のメソッドについて。

Error、Errorf は失敗をマークするが、テスト関数はその先も走る。

テストがどこかで失敗したら、その失敗したところでプロセスを止めたいと思うなら Fatal 系のメソッドを使う。

Setting Up and Tearing Down

(セットアップと分解)

- TestMain

テストの開始前と後処理でやることがあるなら TestMain が状態の管理とテストの実行を助けてくれる。

func TestMain(m *testing.M) {
    // ...
    exitVal := m.Run()
    os.Exit(exitVal)
}
We declare a function called `TestMain` with a parameter of type `*testing.M`. Running `go test` on a package with a `TestMain` function calls the function instead of invoking the tests directly. Once the state is configured, call the `Run` method on `*testing.M` to run the test functions. The `Run` method returns the exit code; 0 indicates that all tests passed. Finally, you must call `os.Exit` with the exit code returned from Run.

`*testing.M` 型をパラメータにして `TestMain` を定義。パッケージにて `go test` を実行するとテストを直に実行するんじゃなくてまず `TestMain` が呼ばれる。状態の設定が済んだら `*testing.M` 型のメソッド `Run` がテスト関数を実行する。`Run` メソッドは exit code を返す(0なら成功)。最後に、`os.Exit` に `Run` メソッドから返ってきた exit code を渡すべし。

Bodner, Jon. Learning Go (p.402). O'Reilly Media. Kindle 版.

・TestMain は一回しか呼ばれない。

・TestMain は一つのパッケージにつき一つまで。

- Cleanup

*teasting.T 型の Cleanup メソッドはテスト後のお掃除のためのコールバック関数を引数で受け取る。

Storing Sample Test Data

As `go test` walks your source code tree, it uses the current package directory as the current working directory. If you want to use sample data to test functions in a package, create a subdirectory named testdata to hold your files. Go reserves this directory name as a place to hold test files. When reading from testdata, always use a relative file reference. Since go test changes the current working directory to the current package, each package accesses its own testdata via a relative file path.

Bodner, Jon. Learning Go (pp.403-404). O'Reilly Media. Kindle 版.

テストに使うデータが testdata という名前のサブディレクトリを作って入れておくと相対パスでアクセスできる。go test はディレクトリを移動しながら実行されるので、プロジェクトのルート・ディレクトリからの相対パスがテスト時に通用しなくなる。

SN

この記事が気に入ったらサポートをしてみませんか?