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
「Chatwork」Android版アプリを 支える単体テストの現在
Search
okuzawats
December 11, 2024
Programming
0
230
「Chatwork」Android版アプリを 支える単体テストの現在
kubell.mobile #2
https://chatwork.connpass.com/event/337364/
での発表資料です。
okuzawats
December 11, 2024
Tweet
Share
More Decks by okuzawats
See All by okuzawats
Androidアプリのモジュール分割における:x:commonを考える
okuzawats
1
300
カンファレンス参加をいかに正当化するか
okuzawats
0
230
「勉強になった」で終わらせない、ストロングスタイルの勉強会
okuzawats
0
350
10年モノのAndroidアプリのコード品質を改善していく、3つの取り組み
okuzawats
0
1.2k
Androidアプリ開発におけるSonarCloudの活用
okuzawats
0
1k
何故、UseCaseは1メソッドなのか
okuzawats
3
1.8k
例外を投げるな、値を返せ
okuzawats
9
7.8k
GitHub ActionsでAndroidアプリのテストを回しまくってたら全プロジェクトのCI/CDが完全停止する寸前だった件
okuzawats
0
530
Kotlinのifを愛でる
okuzawats
0
500
Other Decks in Programming
See All in Programming
Jasprが凄い話
hyshu
0
160
CDK開発におけるコーディング規約の運用
yamanashi_ren01
2
250
AIの力でお手軽Chrome拡張機能作り
taiseiue
0
190
第3回関東Kaggler会_AtCoderはKaggleの役に立つ
chettub
3
1.2k
CDKを使ったPagerDuty連携インフラのテンプレート化
shibuya_shogo
0
110
sappoRo.R #12 初心者セッション
kosugitti
0
280
「個人開発マネタイズ大全」が教えてくれたこと
bani24884
1
190
.NET Frameworkでも汎用ホストが使いたい!
tomokusaba
0
200
苦しいTiDBへの移行を乗り越えて快適な運用を目指す
leveragestech
0
1k
React 19アップデートのために必要なこと
uhyo
8
1.5k
Boos Performance and Developer Productivity with Jakarta EE 11
ivargrimstad
0
310
Bedrock Agentsレスポンス解析によるAgentのOps
licux
3
920
Featured
See All Featured
Easily Structure & Communicate Ideas using Wireframe
afnizarnur
193
16k
Code Reviewing Like a Champion
maltzj
521
39k
Automating Front-end Workflow
addyosmani
1368
200k
Documentation Writing (for coders)
carmenintech
67
4.6k
Cheating the UX When There Is Nothing More to Optimize - PixelPioneers
stephaniewalter
280
13k
StorybookのUI Testing Handbookを読んだ
zakiyama
28
5.5k
Java REST API Framework Comparison - PWX 2021
mraible
29
8.4k
Gamification - CAS2011
davidbonilla
80
5.2k
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
45
9.4k
Fontdeck: Realign not Redesign
paulrobertlloyd
83
5.4k
Designing on Purpose - Digital PM Summit 2013
jponch
117
7.1k
The Psychology of Web Performance [Beyond Tellerrand 2023]
tammyeverts
46
2.3k
Transcript
「Chatwork」Android版アプリを 支える単体テストの現在 2024/12/11 kubell.mobile#2 奥澤俊樹
自己紹介 奥澤 俊樹(@okuzawats) Androidアプリエンジニア / 株式会社kubell ビジネスチャット「Chatwork」 Android版アプリを作っ ています。 髪の毛が伸びる速度が早すぎることが悩みです。
事業概要 *1 Nielsen NetView 及びNielsen Mobile NetView Customized Report 2024年4月度調べ月次利用者(MAU:Monthly
Active User)調査。 調査対象はChatwork、Microsoft Teams、Slack、LINE WORKS、Skypeを含む41サービスを株式会社kubellにて選定。 *2 2024年9月末時点。 • 国内最大級のビジネスチャット「Chatwork」を展開。 業界のパイオニアであり国内利用者数No.1*1、導入社数は60.5万社*2を突破 • 圧倒的な顧客基盤とプラットフォームを背景に、DXされた業務プロセスそのものを提供する クラウドサービス、BPaaSを展開 BPaaS (Business Process as a Service) ビジネスチャット「Chatwork」 お客様 オペレーター
「Chatwork」Android版アプリを 支える単体テストフレームワーク
「Chatwork」Android版アプリ
「Chatwork」Android版アプリ 「Chatwork」はサービス提供開始から10年が経過しており、多くの機能を提供している。 それに比例して複雑なドメイン・ビジネスのルールが存在する。 => 複雑なドメイン・ビジネスのルールに対して、仕様を明確に表す単体テストを書きた い。 ビジネスチャットを提供するアプリという性質上、頻繁に、かつ多量のデータを送受信する 必要がある。通信量やサーバー負荷を低減するために、クライアントサイドのローカルDBに 多くのデータをキャッシュして使用している。 =>
ローカルDBを使用する箇所に対して、信頼性の高い単体テストを書きたい。
「Chatwork」Android版アプリのモジュール構成(簡略版)
「Chatwork」Android版の単体テストを支えるフレームワーク パターン① - JUnit 4 - Robolectric - Truth パターン②
- Kotest - MockK - Truth - Turbine
「Chatwork」Android版アプリのモジュールごとのテストフレームワーク
パターン①:JUnit 4 + Robolectric + 他 - 依存オブジェクトをRobolectricのShadowに置き換えて、テスト対象オブジェクトの単 体テストをできるようにしている。 -
具体的には、テスト対象オブジェクトがSharedPreferenceやSQLiteへの依存を持 つ場合にこちらのパターンで単体テストを書く。 依存オブジェクトをRobolectricの Shadowに置き換える。
パターン②:Kotest + MockK + 他 - 依存オブジェクトをMockKを用いたスタブやスパイに置き換えて、テスト対象オブジェ クトの単体テストをできるようにしている。 - RobolectricのShadowが必要ない場合はこちらのパターンで単体テストを書く。
- 大部分の単体テストはこちらのパターンになる。 依存オブジェクトをMockKを用いた スタブやスパイに置き換える。
各パターンのメリット・デメリット JUnit 4 + Robolectric + 他 Kotest + MockK
+ 他 メリット エミュレータを用いずに、本来は端 末とのインタラクションが必要な処 理の単体テストを、信頼性高く書く ことができる。 Spec形式でテストケースを書くことで、 期待挙動・仕様が明確になる。 コンテキストを分けて、階層的にテスト ケースを書くことができる。 デメリット JUnit 4を用いている場合、一般的に モダンとされるテストコードの書き 方ができない場合がある。 特にKotestの学習コストが高い。 テストコードの書き方に自由度があり、 様々な書き方が混在してしまう。 テストダブルを多用することで単体テスト の信頼性を下げてしまう可能性がある。
単体テストのフレームワーク決定までの経緯 - 元々、JUnit 4で書かれた単体テストとKotestで書かれた単体テストが混在しており、 「どちらを使うべきかわからない」という意見があった。 - 保守・学習コストの観点から、ひとつのフレームワークに統一できることが好ましい。 - 「Spec形式でテストを書きたい、コンテキストごとにテストケースを階層化した い」(=
Kotestを使いたい)という要望あった。 - 機能開発チームはフルスタックなメンバー構成となっており、Spec形式に親 和性があった。 - 複雑なドメイン・ビジネスのルールに対して、仕様を明確に表すことのでき る表現力のある単体テストを書くことは確かに重要。 - 一方、KotestはRobolectricを用いることが難しいという制約があった。 - ローカルDBを使用する箇所はRobolectricを用いて信頼性の高いテストを書きた いので、そのために必須と言えるJUnit 4を使わない判断は難しかった。
単体テストのフレームワーク決定までの経緯 - 「Robolectricが必要な場合はJUnit 4 を、それ以外の場合はKotestを使用す る」という内容のアーキテクチャデシ ジョンレコード(ADR)を書き、メン バーの承認を得て、意思決定・意思統一 を行なった。 -
何故JUnit 4が必要なのか、何故 Kotestが必要なのか、意思決定の 記録を残した。
単体テストのフレームワーク決定までの経緯 - ADR承認後、ADRでの決定に従うように既存のテストコードを書き換えた。 - Robolectricが必要な単体テストはJUnit 4 + Robolectricで、Robolectricが必要 ない単体テストはKotest +
MockKで書くように統一した。 - 元々あった「どちらのフレームワークを使うべきかわからない」という課題につい ては、ADRで方針を明示したこと、既存コードをADRに従って修正したことで解消 できた。
JUnit 4とKotestを使い分けることで得られたこと メリット: - Robolectricを用いることによるデータ層の単体テストの信頼性向上 - Spec形式で単体テストを書くことによる単体テストによる仕様明確化の効果 - 特にドメイン層やViewModelの単体テストで効果大 -
新規メンバーから「期待挙動・仕様がわかりやすかった」とのコメント有 デメリット: - 複数のテストフレームワークを使用していることによる保守コスト・学習コストの増加 - Kotestのテストコードの書き方が統一されていないことによる、テストコードの可読性 ・保守性の低下 - テストコードが書かれた時期、書いたメンバーによって書き方に差がある。
テストピラミッドの観点から考える
テストピラミッドの観点から考える テストピラミッドの観点からは、現状統合テストが足りていない。 理想とされるテストピラミッド 現状のテストピラミッド
テストピラミッドの観点から考える E2Eテスト - 今年から自動化されたE2Eテストにも取り組んでいる。 - アドベントカレンダー見てね! - E2Eテストの導入当初に想定したテストシナリオについて、既に自動化されたテストが 存在する。 統合テスト
- 統合テストについては一部存在するものの、十分な取り組みを行うことができていない ため、今後の課題であると認識している。 - 統合テストの目的設定と、統合テストで何をテストするか?の整理は必要。 - E2Eテストを小さく保つため、E2Eテストの一部のテストシナリオを統合テス トで担保する、ということはあり得る。
まとめ
まとめ - JUnit 4 + Robolectric + 他、Kotest + MockK
+ 他を使い分けることによって、テス ト対象オブジェクトの特性に応じて最適な単体テストを書くことができるようになっ た。 - Kotestで(再び)Robolectricが動くようになると、テストフレームワークが統一 できて嬉しい。 - Kotestは様々なテストコードの書き方ができるため、テストコードが書かれた時期や書 いたメンバーによってテストコードの書き味に差異が出てしまった。 - この点はチームでも課題だと認識しており、今後改善していきたい。 - テストピラミッドの観点を取り入れて、E2Eテスト・統合テスト・単体テストそれぞれ の目的と内容を再定義していくことが、今後は必要になるかもしれない。