Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
mockgenによるモック生成を高速化するツール bulkmockgenのご紹介 / Kyot...
Search
utagawa kiki
July 14, 2023
Programming
2
2.4k
mockgenによるモック生成を高速化するツール bulkmockgenのご紹介 / Kyoto.go #43
Kyoto.go #43
https://kyotogo.connpass.com/event/287778/
utagawa kiki
July 14, 2023
Tweet
Share
More Decks by utagawa kiki
See All by utagawa kiki
自動で //nolint を挿入する取り組み / Gopher's Gathering
utgwkk
1
880
ゆるやかにgolangci-lintのルールを強くする / Kyoto.go #56
utgwkk
2
2.1k
君たちはどうコードをレビューする (される) か / 大吉祥寺.pm
utgwkk
21
15k
Dive into gomock / Go Conference 2024
utgwkk
14
7.3k
Goでリフレクションする、その前に / Kansai.go #1
utgwkk
4
3.4k
Go製Webアプリケーションのエラーとの向き合い方大全、あるいはやっぱりスタックトレース欲しいやん / Kyoto.go #50
utgwkk
7
4.1k
ありがとう、create-react-app
utgwkk
4
11k
SPAでもデータをURLでシェアしたい / Kyoto.js 19
utgwkk
2
1.9k
prototype大全 / YAPC::Kyoto 2023
utgwkk
1
4.6k
Other Decks in Programming
See All in Programming
レトロゲームから学ぶ通信技術の歴史
kimkim0106
0
120
チームで開発し事業を加速するための"良い"設計の考え方 @ サポーターズCoLab 2025-07-08
agatan
1
480
코딩 에이전트 체크리스트: Claude Code ver.
nacyot
0
980
テスト環境にCDを導入してみた
yasaigaoisi
0
100
MCPを使ってイベントソーシングのAIコーディングを効率化する / Streamlining Event Sourcing AI Coding with MCP
tomohisa
0
180
「次に何を学べばいいか分からない」あなたへ──若手エンジニアのための学習地図
panda_program
3
620
チームのテスト力を総合的に鍛えて品質、スピード、レジリエンスを共立させる/Testing approach that improves quality, speed, and resilience
goyoki
5
1.2k
TypeScriptでDXを上げろ! Hono編
yusukebe
3
840
構造化・自動化・ガードレール - Vibe Coding実践記 -
tonegawa07
0
130
副作用と戦う PHP リファクタリング ─ ドメインイベントでビジネスロジックを解きほぐす
kajitack
2
410
抽象化という思考のツール - 理解と活用 - / Abstraction-as-a-Tool-for-Thinking
shin1x1
0
170
商品比較サービス「マイベスト」における パーソナライズレコメンドの第一歩
ucchiii43
0
190
Featured
See All Featured
Connecting the Dots Between Site Speed, User Experience & Your Business [WebExpo 2025]
tammyeverts
8
370
"I'm Feeling Lucky" - Building Great Search Experiences for Today's Users (#IAC19)
danielanewman
229
22k
Optimising Largest Contentful Paint
csswizardry
37
3.3k
Principles of Awesome APIs and How to Build Them.
keavy
126
17k
The Psychology of Web Performance [Beyond Tellerrand 2023]
tammyeverts
48
2.9k
Designing for humans not robots
tammielis
253
25k
Building Adaptive Systems
keathley
43
2.7k
RailsConf 2023
tenderlove
30
1.2k
GraphQLとの向き合い方2022年版
quramy
49
14k
Exploring the Power of Turbo Streams & Action Cable | RailsConf2023
kevinliebholz
34
5.9k
How to Ace a Technical Interview
jacobian
278
23k
A better future with KSS
kneath
238
17k
Transcript
mockgenによるモック生成を 高速化するツール bulkmockgenのご紹介 Kyoto.go #43 @utgwkk (うたがわきき)
自己紹介 @utgwkk (うたがわきき) 株式会社はてな Webアプリケーションエンジニア in 京都 最近はGoを書いて暮らしています
みなさん モックしていますか?
gomock (mockgen) https://github.com/uber/mock (最近 https://github.com/golang/mock がarchiveされた) mockgenでモックを生成してテストで使う
mockgenを使ったモック世界観 (1) // interfaceを定義して type UserStore interface { FindById(ctx context.Context,
id string) (*model.User, error) } // モックを生成する //go:generate mockgen -package mock_store -destination mock_store/user_store.go . UserStore
mockgenを使ったモック世界観 (2) // モックを注入する ctrl := gomock.NewController(t) m := mock_repo.NewMockUserStore(ctrl)
s := NewUserService(s) // モックが呼び出される方法を表明する m.EXPECT().FindById(gomock.Any(), "user"). Return(&model.User{Id: "user"}, nil) // モックを使うメソッドを呼び出してテストする ctx := context.Background() u, err := s.FindUserById(ctx, "user")
mockgen便利 モック生成を一手に引き受けてくれる 便利なmatcherがある (gomock.Any(), gomock.InAnyOrder(), …) 呼び出し方が不正だったらテストを落としてくれる
mockgenの課題 go generateが直列に実行されるので遅い reflect modeだと都度コンパイルされるので遅い
モック生成コマンドが多くなると遅い //go:generate mockgen -package mock_store -destination mock_store/a.go . StoreA //go:generate
mockgen -package mock_store -destination mock_store/b.go . StoreB //go:generate mockgen -package mock_store -destination mock_store/c.go . StoreC go generateによるコード生成は直列に実行される Proposal: cmd/go: parallel execution of //go:generate · Issue #20520 · golang/go
mockgenのreflect modeの仕組み上遅い モックするinterfaceの情報を得るためにGoのプログラムをコンパイルしている mockgenを実行したらコンパイルが走る!!
どんどん遅くなるgo generate 77.70s user 39.76s system 143% cpu 1:21.75 total
https://xkcd.com/303/
go:generate をまとめることはできるが //go:generate mockgen -package mock_store -destination mock_store/store.go . StoreA,StoreB,StoreC
人間がこの1行を編集しまくる必要がある? うまくコンフリクトを解消できる??
bulkmockgen https://github.com/utgwkk/bulkmockgen mockgenのコード生成を1回にまとめて高速化するツールbulkmockgenを作った - 私が 歌川です モック対象のinterfaceをスライスに列挙して一度にコード生成する 移行ツールもある (mockgen-to-bulkmockgen)
仕組み モック対象のinterfaceをスライスに列挙する 静的解析 (go/parser, go/ast) でinterfaceのリストを取得する スライスに渡したinterface名を結合してmockgenに渡す
デモ 大量のinterface定義に対するモック生成を一括で行う https://github.com/utgwkk/bulkmockgen/tree/main/benchmark/interfaces (カンペ: VSCodeを開いてください)
コード生成を速くして効率を上げることに成功 77.70s user 39.76s system 143% cpu 1:21.75 total (before)
52.18s user 19.93s system 209% cpu 34.397 total (after) 関わっているプロジェクトで47秒ほど高速化できた
課題 mockgenが生成するコード中のコメントがコンフリクトする!! // Code generated by MockGen. DO NOT EDIT.
// Source: example.com/test/repo (interfaces: IFoo,IBar,IBaz…)
workaround go generateしたあとにコメントを消す for go_file in `git grep --name-only '^//
Code generated by MockGen. DO NOT EDIT.' -- '*.go'`; do perl -i -nlpe '$_="" if m{// Source: example.com/test/repo}' $go_file gofmt -w $go_file done
まとめ mockgenによるコード生成をまとめるツールbulkmockgenをご紹介 複数のinterfaceのモックを一度に生成することでコード生成を高速化できた interface一覧を1行にまとめる必要がないので人間に優しい
参考 • mockgenのコード生成を1回にまとめて高速化するツールbulkmockgenを作った - 私が歌川です • gomockを完全に理解する • go generateに関するproposal
◦ Proposal: cmd/go: parallel execution of //go:generate · Issue #20520 · golang/go ◦ proposal: cmd/go: generate allow arguments to span multiple lines · Issue #46050 · golang/go
先行研究: gomockhandler Goで大量のモックをより統一的に管理し、もっと高速に生成したい!そうだ!! gomockhandlerを使おう!! | メルカリエンジニアリング mockgenコマンドを並列実行する go generateではなく独自CLIによるモック管理
なぜbulkmockgenを作ったのか go generateの仕組みに乗ったまま高速化できないか考えた 既存の仕組みからジャンプが少ないと導入しやすい モックしたいinterfaceをGoのコードとして列挙するのでrenameにも強い
構想 gomockhandlerとbulkmockgenを組み合わせることができると爆速でモックを生成でき るのでは??