Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Tests in Go

Sponsored · Ship Features Fearlessly Turn features on and off without deploys. Used by thousands of Ruby developers.

Tests in Go

Avatar for Yunosuke Yamada

Yunosuke Yamada

October 16, 2022
Tweet

More Decks by Yunosuke Yamada

Other Decks in Programming

Transcript

  1. type Repository interface { FindAllTodos() ([]Todo, error) } type repository

    struct { db *sql.DB } func (r repository) FindAllTodos() ([]Todo, error) { ... } // 返り値が Repository にできている func NewRepository(db *sql.DB) Repository { return repository{db} } 5
  2. DB アクセスを Repository へ移譲する type UseCase interface { GetTodos() ([]Todo,

    error) } type useCase struct { repoitory Repository } func NewTodoUseCase(repoitory Repository) UseCase { return useCase{ repoitory, } } func (u useCase) GetTodos() ([]Todo, error) { return u.repoitory.FindAllTodos() } 7
  3. mock を使ったテスト func TestGetTodos(t *testing.T) { mockRet := []model.Todo{{ID: 1,

    Content: "Todo1"}} // mock 生成 ctrl := gomock.NewController(t) defer ctrl.Finish() mock := mock_repository.NewMockRepository(ctrl) // 期待する振る舞いを設定 mock.EXPECT().FindAllTodos().Return(mockRet, nil) // 注入 usecase := NewUseCase(mock) actual, _ := usecase.GetTodos() assert.Equal(t, mockRet, actual) } 9
  4. DB のテスト Go に限った話ではないがいくつか方法がある mock を使う方法 比較的簡単だが、DB を使ったときに本当に動くかは分からない。 ORM を使う場合は生成される

    SQL を再現しないといけないかも。 軽量な DB を使う(割愛) 実際の DB を使う方法 mock の逆で、初期化と後処理の方法を考える必要がある。 11
  5. func TestCreateTodo(t *testing.T) { txdb.Register("find_all_todos", "mysql", "dsn") db, _ :=

    sql.Open("find_all_todos", "dsn") defer db.Close() // 最後に閉じてロールバック repo := NewRepository(db) actual, _ := repo.CreateTodo("todo4") assert.Equal(t, &model.Todo{ID: 4, Content: "todo4"}, actual) todos, _ := repo.FindAllTodos() assert.Equal(t, 4, len(todos)) } 13