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
spek
Search
Sponsored
·
Ship Features Fearlessly
Turn features on and off without deploys. Used by thousands of Ruby developers.
→
Shinnosuke Kugimiya
November 21, 2017
Programming
580
1
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
spek
spek
Shinnosuke Kugimiya
November 21, 2017
More Decks by Shinnosuke Kugimiya
See All by Shinnosuke Kugimiya
Claude Code x Androidアプリ 開発
kgmyshin
1
2.5k
AndroidアプリエンジニアもMCPを触ろう
kgmyshin
2
1.4k
15分で分かった気になる dumpsys
kgmyshin
1
370
UIテストはもうMaestroでいいのかもしれない話
kgmyshin
28
13k
新規開発を始めるときにやるべきこと
kgmyshin
19
9.2k
android app error handling
kgmyshin
1
1.6k
solid+cqs+dry
kgmyshin
35
10k
Paging Library ~ アイテムの更新 ~
kgmyshin
2
3.5k
KotlinでReact Native(expo) を使いたい
kgmyshin
2
1.2k
Other Decks in Programming
See All in Programming
メールのエイリアス機能を履き違えない
isshinfunada
0
150
変わらないものが、変わるものを決める — 意図駆動開発 × イベントソーシング × イミュータブル | What Doesn't Change Decides What Can — IDD × Event Sourcing × Immutability
tomohisa
0
710
【やさしく解説 設計編・中級 #6】良いアーキテクチャとは ~ 一本の登り道の、行き先 ~
panda728
PRO
0
190
AI時代に設計が 最大の生産性レバーになる 意図駆動開発とデータを消さない設計|Don't Delete Your Data or Your Intent — Design as the Deepest Lever in the AI Era
tomohisa
0
120
使いながら育てる Claude Code — 開発フローの1コマンド化 × 繰り返し指摘の自動仕組み化
shiki_kakaku
0
1.4k
What's New in Android 2026
veronikapj
0
240
ここ半年くらいでAIに作らせたR用ツール
eitsupi
0
340
torikago - Ruby::Boxで照らすモジュラモノリスの実行境界
se4weed
1
260
言語を使う側から、作る側へ。 自作 Lisp で得た新たな気づき。
andpad
0
140
Build-to-own AI: Agentic Development for Humans
inesmontani
PRO
0
120
php-fpmのプロセスが枯渇した日-調査・対処・そして本当にやるべきだったこと-
shibuchaaaan
0
170
生成AI導入の「期待外れ」を乗り越える ー 開発フロー改革が目指す、真の組織変革
starfish719
0
2.7k
Featured
See All Featured
Evolving SEO for Evolving Search Engines
ryanjones
0
250
SEO for Brand Visibility & Recognition
aleyda
0
4.6k
The Mindset for Success: Future Career Progression
greggifford
PRO
0
430
Fashionably flexible responsive web design (full day workshop)
malarkey
408
67k
Raft: Consensus for Rubyists
vanstee
141
7.6k
Winning Ecommerce Organic Search in an AI Era - #searchnstuff2025
aleyda
1
2.1k
Building Flexible Design Systems
yeseniaperezcruz
330
40k
The State of eCommerce SEO: How to Win in Today's Products SERPs - #SEOweek
aleyda
2
11k
Leveraging Curiosity to Care for An Aging Population
cassininazir
1
440
Dealing with People You Can't Stand - Big Design 2015
cassininazir
367
27k
Practical Orchestrator
shlominoach
191
11k
Intergalactic Javascript Robots from Outer Space
tanoku
273
27k
Transcript
0JTJY4XJGU,PUMJO߹ಉษڧձ
ࣗݾհ w LHNZTIJO ఝٶ Ͱ͢ w "OESPJEΤϯδχΞͰ͢ w "OESPJEΤϯδχΞͰ͢ w
0JTJYͰٕज़ΞυόΠβʔతͳ͜ͱ ͯ͠·͢
4QFLͱ
ίʔυྫ͔Β
·ͣ௨ৗͷςετΛ ݟͯΈΔ
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) }
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) } ςετͱͯ͠ͳ͍͕ɺ Կ͕ࣄલ݅Ͱ ԿΛͨ࣌͠ʹ ԿΛอূ͢Δςετͳͷ͔ ͺͬͱݟΘ͔Βͳ͍
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) } ࣄલ݅
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) } QSFTFOUFSͷPO$SFBUF7JFX͕ݺΕͨ࣌ʹ
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) } WJFXTFU6Q 7JFX.PEFM ͕ݺΕΔ͜ͱΛ͔֬ΊΔςετ
@Test fun onCreateView() { val workId = WorkId(RandomHelper.randomString()) val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) val presenter = WorkDetailPresenter( getWorkUseCase, getEpisodeListUseCase, Schedulers.trampoline(), errorHandler ) presenter.setUp( view, screenTransition, workId.value ) presenter.onCreateView() val expectedViewModel = WorkDetailViewModelConverter.convertToViewModel( work, episodes ) Mockito.verify(view).setUp(expectedViewModel) } WJFXTFU6Q 7JFX.PEFM ͕ݺΕΔ͜ͱΛ͔֬ΊΔςετ ͜ͷΑ͏ʹॱংΛపఈ͢Δ͜ͱ ͦ͏͍͏ॱংͰ͋Δ͜ͱΛ͍ͬͯΔ͜ͱͰ Θ͔Γ͘͢ͳΔ͕ Ͱ͖Δ͜ͱͳΒڧ੍తͩͬͨΓΫϥεͷߏͰ දݱ͍ͨ͠
4QFLͰॻ͍ͨ ςετΛΈΔ
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } }
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { subject.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } } Կ͕ࣄલ݅Ͱ ԿΛͨ࣌͠ʹ ԿΛอূ͢Δςετͳͷ͔ ͺͬͱݟͰΘ͔Δ
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } } ࣄલ݅
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } } QSFTFOUFSͷPO$SFBUF7JFX͕ݺΕͨ࣌ʹ
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } } WJFXTFU6Q 7JFX.PEFM ͕ݺΕΔ͜ͱΛ͔֬ΊΔςετ
given("WorkUseCase return work and EpisodeListUseCase return episodes") { val work
= DomainHelper.work() val episodes = listOf( DomainHelper.episode(), DomainHelper.episode(), DomainHelper.episode() ) Mockito.`when`(workUseCase.execute(workId)).thenReturn(Maybe.just(work)) Mockito.`when`(episodeListUseCase.execute(workId)).thenReturn(Single.just(episodes)) on("onCreateView") { presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkDetailViewModelConverter.convertToViewModel( work, episodeList ) Mockito.verify(view).setUp(expected) } } } WJFXTFU6Q 7JFX.PEFM ͕ݺΕΔ͜ͱΛ͔֬ΊΔςετ Θ͔Δ
4QFLͷࢥ
4QFL w 6OJU5FTUڀۃతʹ༷ͩ w ͋Δঢ়گͰ͋Δ͜ͱΛͨ͠Β͋ΔৼΔ͍Λ͢Δ w ͭ·Γɺ4QFL༷ϑϨʔϜϫʔΫͩ
"OESPJEͷಋೖ
buildscript { repositories { maven { url "http://dl.bintray.com/jetbrains/spek" } }
} 5PQMFWFMCVJMEHSBEMF
dependencies { : testImplementation "org.jetbrains.spek:spek-api:$kotlin_version" testImplementation "org.jetbrains.spek:spek-junit-platform-engine: $kotlin_version" testImplementation "org.jetbrains.spek:spek-subject-extension:
$kotlin_version" // option testImplementation "org.junit.platform:junit-platform-runner:1.0.0" } .PEVMFMFWFMCVJMEHSBEMF
͍ํ
@RunWith(JUnitPlatform::class) class BeforeSeasonWorkListPresenterTest : Spek({ val getBeforeSeasonWorkListUseCase = Mockito.mock(GetBeforeSeasonWorkListUseCase::class.jav given("GetBeforeSeasonWorkListUseCase
return workList") { val works = DomainHelper. works() Mockito.`when`(getBeforeSeasonWorkListUseCase.execute()).thenReturn(Single.just(works)) on("onCreateView") { val presenter = BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkViewModelConverter.convertToViewModel(works) Mockito.verify(view).setUp(expected) } } } given("") { on("onClickWork") { val viewModel = WorkViewModelFactory.create() val presenter = BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) presenter.onClickWork(viewModel) it("should move to Detail") { Mockito.verify(screenTransition).moveToDetail() } } } })
@RunWith(JUnitPlatform::class) class BeforeSeasonWorkListPresenterTest : Spek({ val getBeforeSeasonWorkListUseCase = Mockito.mock(GetBeforeSeasonWorkListUseCase::class.jav given("GetBeforeSeasonWorkListUseCase
return workList") { val works = DomainHelper. works() Mockito.`when`(getBeforeSeasonWorkListUseCase.execute()).thenReturn(Single.just(works)) on("onCreateView") { val presenter = BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) presenter.onCreateView() it("should setUp ViewModel to view") { val expected = WorkViewModelConverter.convertToViewModel(works) Mockito.verify(view).setUp(expected) } } } given("") { on("onClickWork") { val viewModel = WorkViewModelFactory.create() val presenter = BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) presenter.onClickWork(viewModel) it("should move to Detail") { Mockito.verify(screenTransition).moveToDetail() } } } }) HJWFO PO JUΛͬͯςετΛॻ͚ͩ͘
4VCKFDU4QFL
@RunWith(JUnitPlatform::class) internal class BeforeSeasonWorkListPresenterSpec : SubjectSpek<BeforeSeasonWorkListPresenter>({ val getBeforeSeasonWorkListUseCase = Mockito.mock(GetBeforeSeasonWorkListUseCase::class.java)
subject { BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) } given("GetBeforeSeasonWorkListUseCase return workList") { val works = DomainHelper.works() Mockito.`when`(getBeforeSeasonWorkListUseCase.execute()).thenReturn(Single.just(works)) on("onCreateView") { subject.onCreateView() it("should setUp ViewModel to view") { val expected = WorkViewModelConverter.convertToViewModel(works) Mockito.verify(view).setUp(expected) } } } given("") { on("onClickWork") { val viewModel = WorkViewModelFactory.create() subject.onClickWork(viewModel) it("should move to Detail") { Mockito.verify(screenTransition).moveToDetail() } } } })
@RunWith(JUnitPlatform::class) internal class BeforeSeasonWorkListPresenterSpec : SubjectSpek<BeforeSeasonWorkListPresenter>({ val getBeforeSeasonWorkListUseCase = Mockito.mock(GetBeforeSeasonWorkListUseCase::class.java)
subject { BeforeSeasonWorkListPresenter(getBeforeSeasonWorkListUseCase) } given("GetBeforeSeasonWorkListUseCase return workList") { val works = DomainHelper.works() Mockito.`when`(getBeforeSeasonWorkListUseCase.execute()).thenReturn(Single.just(works)) on("onCreateView") { subject.onCreateView() it("should setUp ViewModel to view") { val expected = WorkViewModelConverter.convertToViewModel(works) Mockito.verify(view).setUp(expected) } } } given("") { on("onClickWork") { val viewModel = WorkViewModelFactory.create() subject.onClickWork(viewModel) it("should move to Detail") { Mockito.verify(screenTransition).moveToDetail() } } } }) ςετରΫϥε͕Θ͔Γ͍͢
ଞʹ w HJWFOPOJU͚ͩͰͳ͘EFTDSJCFJUͷܗͰॻ͚ Δ w CFGPSF(SPVQ BGUFS&BDI5FTUͳͲϑοΫͰ͖Δ w NFNPJ[FEͰॻ͘ςετͷͨͼʹ࡞Γͨ͠ΓͰ ͖Δ
w YQSFpYΛ͚ͭΕQFOEJOHʹͰ͖Δ YHJWFO YJUͳ Ͳ
Ҿ͔͔ͬͬͨΓͨ͠ͱ ͜Ζ
Ҿ͔͔ͬͬͨΓͨ͠ͱ͜Ζᶃ w !3VO8JUI +6OJU1MBUGPSNDMBTT Λ͚ͭͳ͍ͱೝ ࣝ͞Εͳ͍ w UFTUΛΒͤͨͱ͖ʹɺGBJM͞ΕΔͣͷςετ ͕GBJM͠ͳ͍ͷͰؾ͔ͮͳ͍Մೳੑ͕͋Δ ˞+6OJUͳΒ͚ͭͳ͍͍ͯ͘
Έ͍ͨ
Ҿ͔͔ͬͬͨΓͨ͠ͱ͜Ζᶄ ύοέʔδใ͕ফ͑Δʜ
Ҿ͔͔ͬͬͨΓͨ͠ͱ͜Ζᶄ Ͳͷςετ͔Θ͔ΓͮΒ͍
Ҿ͔͔ͬͬͨΓͨ͠ͱ͜Ζᶅ Spek { val a: A = Mockito.mock(A::class.java) given() {
Mockito.when(a.execute).thenReturn("a") on() { it() { assertEquals("a", a.execute) } } } } ͜ͷςετ1BTT 'BJM
Ҿ͔͔ͬͬͨΓͨ͠ͱ͜Ζᶅ Spek { val a: A = Mockito.mock(A::class.java) given() {
Mockito.when(a.execute).thenReturn("a") on() { it() { assertEquals("a", a.execute) } } } } 1BTT
Spek { val a: A = Mockito.mock(A::class.java) given() { Mockito.when(a.execute).thenReturn("a")
on() { it() { assertEquals("a", a.execute) } } } given() { Mockito.when(a.execute).thenReturn("b") on() { it() { assertEquals("b", a.execute) } } } } ͜ͷςετ1BTT 'BJM
Spek { val a: A = Mockito.mock(A::class.java) given() { Mockito.when(a.execute).thenReturn("a")
on() { it() { assertEquals("a", a.execute) } } } given() { Mockito.when(a.execute).thenReturn("b") on() { it() { assertEquals("b", a.execute) } } } }
Spek { val a: A = Mockito.mock(A::class.java) given() { Mockito.when(a.execute).thenReturn("a")
on() { it() { assertEquals("a", a.execute) } } } given() { Mockito.when(a.execute).thenReturn("b") on() { it() { assertEquals("b", a.execute) } } } } 1BTT 'BJM
Spek { val a: A = Mockito.mock(A::class.java) given() { Mockito.when(a.execute).thenReturn("a")
on() { it() { assertEquals("a", a.execute) } } } given() { Mockito.when(a.execute).thenReturn("b") on() { it() { assertEquals("b", a.execute) } } } } ͬͱԼʹ͋Δͷউͪ
Spek { val a: A = Mockito.mock(A::class.java) given() { beforeGroup
{ Mockito.when(a.execute).thenReturn(“a”) } on() { it() { assertEquals("a", a.execute) } } } given() { beforeGroup { Mockito.when(a.execute).thenReturn(“b”) } on() { it() { assertEquals("b", a.execute) } } } ͜͏͠·͠ΐ͏
·ͱΊ
·ͱΊ w Ϣχοτςετͱ͢ͳΘ༷ͪͩʂ w 4QFL༷ϑϨʔϜϫʔΫͩʂ w HJWFOPOJUͰςετΛॻ͜͏ w 4VCKFDU4QFLͰςετରΛ໌֬ʹ w
ͪΖΜσϝϦοτ͋Δ
࣮ࡍʹͬͯΔ༷Λ ݟ͍ͨํͪ͜Β͔Β w IUUQTHJUIVCDPNLHNZTIJOBOOJDUBOESPJE