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
UI State設計とテスト方針
Search
rmakiyama
December 20, 2024
Technology
4
1k
UI State設計とテスト方針
Ebisu.mobile #8 大忘年会 STORES kubell Kyash asken
https://hey.connpass.com/event/335971/
rmakiyama
December 20, 2024
Tweet
Share
More Decks by rmakiyama
See All by rmakiyama
KMPプロジェクトでマニュアルDIを使う選択
rmakiyama
0
320
Jetpack Composeとデザインシステム
rmakiyama
0
900
TextField theme in Compose
rmakiyama
0
270
Androidエンジニアが1人という不安と向き合う
rmakiyama
6
6.7k
Jetpack Compose Canvas入門
rmakiyama
0
1.4k
HiltはDIをどうやってやっているのか
rmakiyama
1
270
Radiotalk Androidアプリにおけるモジュール分割の課題とこれから
rmakiyama
1
300
Androidでオーディオアプリを作るということ
rmakiyama
1
3.3k
getChangePayload in DiffUtil
rmakiyama
0
3.1k
Other Decks in Technology
See All in Technology
OPENLOGI Company Profile
hr01
0
63k
Terraform Cloudで始めるおひとりさまOrganizationsのすゝめ
handy
2
210
Compose におけるパスワード自動入力とパスワード保存
tonionagauzzi
0
150
ビジネスとデザインとエンジニアリングを繋ぐために 一人のエンジニアは何ができるか / What can a single engineer do to connect business, design, and engineering?
kaminashi
2
790
意思決定を支える検索体験を目指してやってきたこと
hinatades
PRO
0
340
AIエージェント開発手法と業務導入のプラクティス
ykosaka
9
2.5k
コスト最適重視でAurora PostgreSQLのログ分析基盤を作ってみた #jawsug_tokyo
non97
1
810
Стильный код: натуральный поиск редких атрибутов по картинке. Юлия Антохина, Data Scientist, Lamoda Tech
lamodatech
0
840
C++26アップデート 2025-03
faithandbrave
0
1.1k
ここはMCPの夜明けまえ
nwiizo
32
12k
AIにおけるソフトウェアテスト_ver1.00
fumisuke
1
300
QA/SDETの現在と、これからの挑戦
imtnd
0
160
Featured
See All Featured
実際に使うSQLの書き方 徹底解説 / pgcon21j-tutorial
soudai
178
53k
Become a Pro
speakerdeck
PRO
28
5.3k
Build your cross-platform service in a week with App Engine
jlugia
230
18k
[RailsConf 2023 Opening Keynote] The Magic of Rails
eileencodes
29
9.4k
The Cult of Friendly URLs
andyhume
78
6.3k
Dealing with People You Can't Stand - Big Design 2015
cassininazir
367
26k
The Language of Interfaces
destraynor
157
25k
Distributed Sagas: A Protocol for Coordinating Microservices
caitiem20
331
21k
XXLCSS - How to scale CSS and keep your sanity
sugarenia
248
1.3M
Practical Tips for Bootstrapping Information Extraction Pipelines
honnibal
PRO
19
1.2k
Site-Speed That Sticks
csswizardry
6
510
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
45
9.5k
Transcript
©2024 Kyash Inc. ©2024 Kyash Inc. UI State設計とテスト方針 2024/12/20 rmakiyama(MAKIYAMA
Ryo) Ebisu.mobile #8 大忘年会 STORES kubell Kyash asken
©2024 Kyash Inc. 2 • Kyash Inc (2022/10 -) •
Android Engineer • Engineering Manager • @_rmakiyama • @rmakiyama MAKIYAMA Ryo 自己紹介
©2024 Kyash Inc. 3 Kyashについて お支払いも お金の管理も かんたんに Visaプリペイドカードとスマホで、いつでもどこでも、かんたんにお支払い。 アプリへのリアルタイムな履歴反映や自動カテゴリー分類で、お金の管理もかんたんに。
©2024 Kyash Inc. KyashとJetpack Compose • 2021年5月から導入開始 • Fragmentの上にComposeViewを載せる運用 •
新規実装する画面は基本的にJetpack Composeを利用 • 大小含め100画面以上を実装 Jetpack Composeがデファクトスタンダード 4 ※2024年5月現在
©2024 Kyash Inc. アジェンダ • KyashのKotlin Multiplatform構成 ◦ Reactor概説 ◦
UI Stateのサンプル • UI Stateの設計で考えていること • テスト方針 UI State設計とテスト方針 5
©2024 Kyash Inc. KyashのKMP構成概略 6 • ReactorKitを汲んだMVIライクな設計 ◦ State/Action/Event •
各OSでWrapper実装がある
©2024 Kyash Inc. KyashのKMP構成概略 / UI Layer 7
©2024 Kyash Inc. KyashのKMP構成概略 / UI Layer / Reactor 8
class InputAmountReactor( mainDispatcher: CoroutineDispatcher, ) : AbstractReactor<Reactor.LoadState<State>, Action, Mutation, Event>( mainDispatcher = mainDispatcher, initialState = Reactor.LoadState.Loading(), ) { override fun mutate(action: Action): Flow<Mutation> = flow {...} override fun reduce( state: Reactor.LoadState<State>, mutation: Mutation, ): Reactor.LoadState<State> = when (mutation) {...} data class State(...) : Reactor.State sealed class Action : Reactor.Action sealed class Mutation : AbstractReactor.Mutation sealed class Event : Reactor.Event }
©2024 Kyash Inc. ©2024 Kyash Inc. UI State設計⚒ 9 9
©2024 Kyash Inc. ©2024 Kyash Inc. 簡単なサンプル 10 10
©2024 Kyash Inc. Sample app 11
©2024 Kyash Inc. Sample app 12 • 金額を入力してOKをおしてSubmit • 金額を入力しないとOKが押せない
• 1000円以上でないとエラーとする
©2024 Kyash Inc. Sample app / UI State 13 data
class UiState( val amount: Long?, )
©2024 Kyash Inc. Sample app / UI State 14 data
class UiState( val amount: Long?, ) 🤔
©2024 Kyash Inc. Sample app / UI State 15 data
class UiState( val amount: Long?, ) : Reactor.State { val hasError: Boolean = amount &= null && amount &= 0L && amount < 1000L val buttonEnabled: Boolean = amount &= null && isError.not() }
©2024 Kyash Inc. Sample app / UI State 16 data
class UiState( val amount: Long?, ) : Reactor.State { val hasError: Boolean = amount &= null && amount &= 0L && amount < 1000L val buttonEnabled: Boolean = amount &= null && isError.not() } 関心の分離ができている! 仕様・振る舞いが見えてくる!
©2024 Kyash Inc. UI Stateの設計で考えていること UI Stateで仕様や振る舞いを表現する • 見た目(Element)と状態(State)で関心の分離をする ◦
Composable関数を簡単にレンダリングできるデータとして定義 • UIの理解容易性とテスタビリティを高める • ※ 網羅性を意識しすぎない 17 https://developer.android.com/topic/architecture/ui-layer
©2024 Kyash Inc. ©2024 Kyash Inc. テスト方針🧪 18 18
©2024 Kyash Inc. 2024年現在のKyashアプリのテスト方針 State Holder / UI Stateの ユニットテストを重点的にやる
• Reactorのユニットテストを最低限行う ◦ Actionに対するStateの期待値をテスト ◦ 状態遷移のテストはUI Stateに対するテスト • UIの振る舞いのテストの一部をカバー ◦ UI Stateの責務の工夫とセット 19
©2024 Kyash Inc. 2024年現在のKyashアプリのテスト方針の背景 問題をできるだけ早い段階で検出し 開発/アウトカムのフィードバックループを早めたい • KMPだとユニットテストのROIが高い ◦ バグの検出コストを最小限に抑える
• UIテストの責務を絞り効果を高める ◦ テストの関心を分離 ◦ UIロジックや外観のテストにフォーカス 20
©2024 Kyash Inc. Thank you!! • UIを見た目(Element)と状態(State)に分けてUI Stateを設計している ◦ UI
Stateで仕様や振る舞いを表現 • State Holder/UI Stateのテストで仕様や振る舞いのテストを一部カバー • みんなはどうやってる?このあと話しましょう!! まとめ 21
©2024 Kyash Inc. Last one… • モバイルエンジニアを募集中です! • 懇親会でも気軽に話しましょう! WE
ARE HIRING 22 エンジニアの求人一覧 Advent Calendar 2024
©2024 Kyash Inc.
©2024 Kyash Inc. Appendix 24 https://www.wantedly.com/companies/wantedly/post_articles/300999 https://developer.android.com/topic/architecture/ui-layer?hl=ja https://developer.android.com/topic/architecture/ui-layer/stateholders?hl=ja https://developer.android.com/develop/ui/compose/migrate/other-considerations?hl=ja#prio ritize-splitting-state
https://developer.android.com/training/testing/fundamentals/strategies?hl=ja https://developer.android.com/training/testing/fundamentals?hl=ja