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
約9000個の自動テストの 時間を50分->10分に短縮 Flakyテストを1%以下に抑えた話
Search
hatsu
October 25, 2024
Programming
24
15k
約9000個の自動テストの 時間を50分->10分に短縮 Flakyテストを1%以下に抑えた話
hatsu
October 25, 2024
Tweet
Share
More Decks by hatsu
See All by hatsu
introduction_scriptor_gem.pdf
hatsu38
1
96
Just a Rails Patch Update
hatsu38
2
620
Dive into MaintenanceTasks
hatsu38
1
130
GitHub Actions is Fun
hatsu38
1
150
Other Decks in Programming
See All in Programming
From the Wild into the Clouds - Laravel Meetup Talk
neverything
0
190
Lambdaの監視、できてますか?Datadogを用いてLambdaを見守ろう
nealle
2
840
変化の激しい時代における、こだわりのないエンジニアの強さ
satoshi256kbyte
1
830
❄️ NixOS/nixpkgsにSATySFiサポートを実装する
momeemt
1
100
CDKを使ったPagerDuty連携インフラのテンプレート化
shibuya_shogo
0
130
iOSでQRコード生成奮闘記
ktcryomm
2
140
バイセルでの AI を用いた開発の取り組み ~ Devin, Cursor の活用事例・知見共有 ~
umaidashi
0
110
たのしいSocketのしくみ / Socket Under a Microscope
coe401_
8
1.5k
CDK開発におけるコーディング規約の運用
yamanashi_ren01
2
270
Serverless Rust: Your Low-Risk Entry Point to Rust in Production (and the benefits are huge)
lmammino
1
170
PHPのバージョンアップ時にも役立ったAST
matsuo_atsushi
0
240
Devin入門 〜月500ドルから始まるAIチームメイトとの開発生活〜 / Introduction Devin 〜Development With AI Teammates〜
rkaga
3
1.4k
Featured
See All Featured
Cheating the UX When There Is Nothing More to Optimize - PixelPioneers
stephaniewalter
280
13k
What’s in a name? Adding method to the madness
productmarketing
PRO
22
3.3k
Improving Core Web Vitals using Speculation Rules API
sergeychernyshev
11
560
The Language of Interfaces
destraynor
156
24k
Building Adaptive Systems
keathley
40
2.4k
Git: the NoSQL Database
bkeepers
PRO
429
65k
What's in a price? How to price your products and services
michaelherold
244
12k
Build your cross-platform service in a week with App Engine
jlugia
229
18k
[RailsConf 2023] Rails as a piece of cake
palkan
53
5.3k
A designer walks into a library…
pauljervisheath
205
24k
No one is an island. Learnings from fostering a developers community.
thoeni
21
3.2k
Automating Front-end Workflow
addyosmani
1369
200k
Transcript
9000ݸͷࣗಈςετͷ ࣌ؒΛ50->10ʹॖ FlakyςετΛ1%ҎԼʹ͑ͨ Kaigi on Rails 2024 @hatsu_38 2024/10/26
εϥΠυ1ຕʹ͖ͭ6ඵͷϖʔεͰਐ· ͳ͍ͱؒʹ߹͍ͳ͍ܭࢉʹͳΓ·͠ ͨɻͦͷϖʔεͰਐΉ͜ͱྃ͝ঝͩ͘ ͍͞🙏
ࣗݾհ • Twitter: @hatsu_38 • GitHub: @hatsu38 • SHE Inc.
• Rubyྺ 5 = ΤϯδχΞྺ • React.js / TypeScript / GitHub Actions • Ruby͕Ұ൪͖
CIͰࣗಈςετ ࣮ߦ͍ͯ͠·͔͢ʁ🙋
ࣗಈςετ 10Ҏ্͔͔͍ͬͯ·͔͢ʁ🙋
Initial Commit2017 ฐࣾͷ͜ͱ🏢
ٕज़ελοΫ🤖 • Backend: Ruby on Rails, GraphQL, Sidekiq • Frontend:
React.js, TypeScript, Next.js • CI: GitHub Actions • Infrastructure: Kubenetes ฐࣾͷ͜ͱ🏢 7
2023ͷࣗಈςετͷঢ়گ🔍 ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍
Model / Controller / Requests / System Spec, etc. ςετ
7,803 case 2023.05.22 34QFD $BQZCBSBΛར༻ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍 Code to Test Ratio: 1:4.3 Test Coverage: 89%
Model / Controller / Requests / System Spec, etc. ςετ࣌ؒ
ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍 $*͕௨ΔͷʹҎ্🫠
Flakyͳςετࢁ💥 ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍 ࣮ߦ݁Ռ͕ ෆ҆ఆͳςετ
ཧͷCIͷ࣌ؒ10Ҏɺ Έ͍ͨͳจষΛҾ༻͢Δ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍
ཧͷCIͷ࣌ؒ10Ҏɺ Έ͍ͨͳจষΛҾ༻͢Δ $*ͷεϐʔυେͰ͢ɻ ཧҎɺ͘ͱҎʹྃͤ͞·͠ΐ͏ɻ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍
ཧͷCIͷ࣌ؒ10Ҏɺ Έ͍ͨͳจষΛҾ༻͢Δ $*ͷεϐʔυେͰ͢ɻ ཧҎɺ͘ͱҎʹྃͤ͞·͠ΐ͏ɻ ϑϨʔΩʔςετͷ͕͖͍͠Λ͑Δͱɺ ςετશମ͕৴པ͞Εͳ͘ͳΔͷͰ͢ɻͦͷ͖͍͠Ͱ͢ɻ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍
վળ͠Α͏🛠⚙ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍
ςετ DBTF $*ͷ࣌ؒ ฒྻ$PSF 'MBLZςετ ݸ
͘Β͍ͷ֬Ͱ$*͕མͪΔ (JU)VC"DUJPOTͷஈ ฐࣾͷ͜ͱ - 2023ͷςετͷঢ়گ🔍 2023ͷςετͷঢ়گ🔍
͜Ε͔Βɺͬͨ͜ͱΛ ͨ͘͞Μհ͍͖ͯ͠·͢💡
ࣗࣾͰ͑ͦ͏ͳ5JQT ෦͜Μͳ࣮Ͱಈ͍͍ͯΔΜͩ ͬͯൃݟ͕1ͭ͋Εྑ͍ͳͱ💯💡
ͭͷ՝💥 • ςετͷ͕͍࣌ؒ🐢 • ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ʢগ͠3VCZ͔Βઢʣ • Flakyͳςετ͕ଟ͍💫
ͭͷ՝💥 • ςετͷ͕͍࣌ؒ🐢 • ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ʢগ͠3VCZ͔Βઢʣ • Flakyͳςετ͕ଟ͍💫
• CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 21 ςετͷ͕͍࣌ؒ🐢
• CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 22 ςετͷ͕͍࣌ؒ🐢
Sleep͕59Օॴ͋ͬͨ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ
Sleep͕ΘΕ͍ͯΔྫ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ ϑΥʔϜೖྗͯ͠ɺอଘ͢ΔϘλϯԡͨ͠Βɺ
Sleep͕ΘΕ͍ͯΔྫ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ
have_text(“hoge”)ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ
have_text(“hoge”)ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ
have_text(“hoge”)ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ EFGBVMU@NBY@XBJU@UJNF σϑΥϧτ ඵؒ୳͠ଓ͚Δඵͷઃఆ ͜ͷඵͷؒɺςΩετzIPQFzΛ୳ͯ͘͠ΕΔ
have_text(“hoge”)ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ EFGBVMU@SFUSZ@JOUFSWBM σϑΥϧτ ඵςΩετzIPHFzΛ܁Γฦ͠୳ִؒ͢ EFGBVMU@NBY@XBJU@UJNF σϑΥϧτ ඵؒ୳͠ଓ͚Δඵͷઃఆ
͜ͷඵͷؒɺςΩετzIPQFzΛ୳ͯ͘͠ΕΔ
have_text(“hoge”)ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ ͜Ε͕retryͰ܁Γฦ͠ಈ͘ EFGBVMU@NBY@XBJU@UJNF σϑΥϧτ ඵؒ୳͠ଓ͚Δඵͷઃఆ ͜ͷඵͷؒɺςΩετzIPQFzΛ୳ͯ͘͠ΕΔ EFGBVMU@SFUSZ@JOUFSWBM
σϑΥϧτ ඵςΩετzIPHFzΛ܁Γฦ͠୳ִؒ͢
Sleep͕59 30Օॴʹݮͬͨ✨ CapybaraͷػೳʹͤͯSleepΛআ
Capybaraͷػೳʹͤͯ SleepΛআ ςετͷ͕͍࣌ؒ🐢 - CapybaraͷػೳʹͤͯSleepΛআ खܰ͞: ˒˒˒˒˒ ޮՌ: ˒˒˒ˑˑ
• CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelperΛ࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 33 ςετͷ͕͍࣌ؒ🐢
Sleep͕30Օॴ͋ͬͨ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ
Sleep͕ΘΕ͍ͯΔྫ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ > default_max_wait_time
LoadingΞΠίϯ͕ফ͑ΔͷΛͭHelperΛ࡞ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ ಈతʹ-PBEJOHΞΠίϯ͕ফ͔͑ͨͲ͏͔ ܁Γฦ֬͠ೝ͢Δ
LoadingΞΠίϯ͕ফ͑ΔͷΛͭHelperΛ࡞ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ ಈతʹ-PBEJOHΞΠίϯ͕ফ͔͑ͨͲ͏͔ ܁Γฦ֬͠ೝ͢Δ ͜͜ʹHTMLͷSelectorΛࢦఆ
LoadingΞΠίϯ͕ফ͑ΔͷΛͭHelperΛར༻ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ $BQZCBSBͷEFGBVMU@NBY@XBJU@UJNFͰ-PBEJOH͕ ऴΘΒͳ͍߹ʹར༻
Sleep͕59 30 13Օॴʹݮͬͨ✨ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ
LoadingΛಈతʹͭHelperΛ ࡞ͬͯSleepΛআ ςετͷ͕͍࣌ؒ🐢 - LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ खܰ͞: ˒˒˒ˑˑ ޮՌ: ˒˒˒˒ˑ
• CapybaraͷػೳʹͤͯSleepআ • LoadingΛಈతʹͭHelperΛ࡞ͬͯSleepআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 41 ςετͷ͕͍࣌ؒ🐢
σʔλ࡞͕25,550݅ - 35݅ͷςετ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ →ςετ࣌ؒ1m24sͷ͏ͪ1m4s͕σʔλੜ test-prof gemͰௐࠪ
σʔλ࡞͕25,550݅ - 35݅ͷςετ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ → Seedσʔλͷ࡞Λߦ͏εΫϦϓτ 1Ͱ675݅ͷσʔλΛ࡞͢Δ JSC
NBJO
Seedσʔλ࡞εΫϦϓτ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ ଞͷςετͰ͍·Θͤͦ͏💡
σʔλ࡞͕25,550݅ - 35݅ͷςετ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ before_allͰSeedσʔλΛ͍ճ͢
before_all { Fixtures.setup }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ
before_all { Fixtures.setup }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ ςετάϧʔϓશମʹରͯ͠
before_all { Fixtures.setup }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ ςετάϧʔϓશମʹରͯ͠ τϥϯβΫγϣϯΛுͬͯ ͦͷதͰblockΛݺͼग़͢
before_all { Fixtures.setup }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ ςετάϧʔϓશମʹରͯ͠ τϥϯβΫγϣϯΛுͬͯ ͦͷதͰblockΛݺͼग़͢
ςετάϧʔϓͷςετ͕ऴΘͬͨΒ Rollback͢Δ
σʔλ࡞͕25,550݅ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ →ςετ࣌ؒ1m24sͷ͏ͪ1m4s͕σʔλੜ(ςετέʔε35έʔε) test-prof gemͰௐࠪ
σʔλ࡞͕25,550 2,600݅ʹݮͬͨ✨ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ ςετ࣌ؒ1m24s->40sʹॖ test-prof gemͰௐࠪ
test-profͷbefore_allΛͬͯ σʔλ࡞Λলུ ςετͷ͕͍࣌ؒ🐢 - test-profͷbefore_allΛͬͯσʔλ࡞Λলུ खܰ͞: ˒˒˒˒ˑ ޮՌ: ˒˒˒˒˒
• CapybaraͷػೳʹͤͯSleepআ • LoadingΛಈతʹͭHelperΛ࡞ͬͯSleepআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 53 ςετͷ͕͍࣌ؒ🐢
σʔλ࡞͕37,530݅ - 675݅ͷςετ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ →ςετ࣌ؒ2m50sͷ͏ͪ2m1s͕σʔλੜ test-prof gemͰௐࠪ
σʔλ࡞͕37,530݅ - 675݅ͷςετ ྫ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ
σʔλ࡞͕37,530݅ - 675݅ͷςετ ྫ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ →ςετͷͨͼʹݺΕΔ
σʔλ࡞͕37,530݅ - 675݅ͷςετ ྫ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ ͕ɺຖ࡞Γ͞ͳͯ͘ಉ͡ΠϯελϯεΛ͍·ͤΔม💡 →ςετͷͨͼʹݺΕΔ
letΛଞͷςετͰ͍ճ͢ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ
let_it_be(:admin) { create(:user) }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ
let_it_be(:admin) { create(:user) }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ proc { @😸admin
= create(:user) }
let_it_be(:admin) { create(:user) }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ proc { @😸admin
= create(:user) } before_all { @😸admin = create(:user) }
let_it_be(:admin) { create(:user) }ͰԿ͕ى͖͍ͯΔ͔ʁ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ proc { @😸admin
= create(:user) } before_all { @😸admin = create(:user) } let(:admin) { @😸admin } (`@😸admin` before_allͰ࡞ࡁΈ)
σʔλ࡞͕37,530݅ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ →ςετ࣌ؒ2m50sͷ͏ͪ2m1s͕σʔλੜ test-prof gemͰௐࠪ
σʔλ࡞͕37,530 4,970݅ʹݮͬͨ✨ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ ςετ࣌ؒ2m50s->37s test-prof gemͰௐࠪ
test-profͷlet_it_beΛͬͯ σʔλ࡞Λলུ ςετͷ͕͍࣌ؒ🐢 - test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ खܰ͞: ˒˒˒˒ˑ ޮՌ: ˒˒˒˒ˑ
• CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelperΛ࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳ͋Ε͜Ε ςετͷ͕͍࣌ؒ🐢 66 ςετͷ͕͍࣌ؒ🐢
parallel_testsͱʁ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ $16@ .ݸͷ ςετϑΝΠϧ $16@ /ݸͷ ςετϑΝΠϧ
ɾɾɾ $16@9 ,ݸͷ ςετϑΝΠϧ CPUݸʹςετϑΝΠϧΛׂͯ͠ɺ ςετΛฒྻʹ࣮ߦͤ͞Δ💡
ޮͷѱׂ͍ - 1,000s ͔͔Δ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ user_spec.rb ͕ංେԽ
ޮͷѱׂ͍ - 1,000s ͔͔Δ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ $16T $16 T
ޮͷྑׂ͍ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ T͔͔ΔςετϑΝΠϧΛͭʹׂ $16 T
ޮͷྑׂ͍ - 600sͰऴΘΔ✨ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ $16T $16T
ޮͷྑׂ͍ - ࣮ྫ parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ Before After
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘͯ͠ྻΛ࡞ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 73
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 74
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘͯ͠ྻΛ࡞ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 75 [ςετ໊, ςετϑΝΠϧByte]
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 76 ͜ͷྻΛϑΝΠϧαΠζͷ߱ॱʹSort
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 77 $16 $16 $16 $16
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 78 $16 $16 $16 $16 ,ݸͷ ςετϑΝΠϧ .ݸͷ ςετϑΝΠϧ /ݸͷ ςετϑΝΠϧ -ݸͷ ςετϑΝΠϧ
parallel_testsͰԿ͕ى͖ͯΔʁ(ྫ: fi le size sort) 1. CPUίΞΛऔಘͯ͠ 2. ςετରͷϑΝΠϧͷϑΝΠϧαΠζ(byte)Λऔಘ 3.
ϑΝΠϧαΠζͷେ͖͍ॱʹฒͼସ͑ͯ 4. CPUݸͷάϧʔϓΛ࡞ͬͯ 5. ϑΝΠϧαΠζͷେ͖͍ॱʹɺ߹ܭϑΝΠϧαΠζͷ࠷খ͍͞ά ϧʔϓʹɺϑΝΠϧΛՃΛ܁Γฦͯ͠άϧʔϓ࡞ 6. ֤$16ͰςετΛ࣮ߦ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ 79
parallel_testsͷฒྻ࣮ߦΛ׆͔͢ ͨΊʹϑΝΠϧׂ ςετͷ͕͍࣌ؒ🐢 - parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ खܰ͞: ˒˒˒˒ˑ ޮՌ: ˒˒˒˒ˑ
• CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelperΛ࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ • parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ
• ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ ςετͷ͕͍࣌ؒ🐢 81 ςετͷ͕͍࣌ؒ🐢
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 82
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 83 खܰ͞: ˒˒˒˒ˑ ޮՌ: ˒˒ˑˑˑ
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 84 Bad Good खܰ͞: ˒˒˒ˑˑ ޮՌ: ˒˒˒ˑˑ
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 85 खܰ͞: ˒˒˒ˑˑ ޮՌ: ˒˒˒ˑˑ
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 86 खܰ͞: ˒˒ˑˑˑ ޮՌ: ˒˒ˑˑˑ
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 87 खܰ͞: ˒ˑˑˑˑ ޮՌ: ˒˒˒ˑˑ
ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do ~
endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμογϡϘʔυԽ ςετͷ͕͍࣌ؒ🐢 - ͦͷଞɺࡉ͔ͳςετ࣌ؒॖͷͨΊͷࢪࡦ 88 खܰ͞: ˒ˑˑˑˑ ޮՌ: ˒˒ˑˑˑ
CIͷ͕࣌ؒ54->23✨ ςετͷ͕͍࣌ؒ🐢 5FTU NT #VJME NT 3FQPSU T
લઓऴྃ🍻 ʢͨͿΜ12͘Β͍ܦաதʣ
CIͷ͕࣌ؒ54->23✨ ςετͷ͕͍࣌ؒ🐢 5FTU NT #VJME NT 3FQPSU T
CIͷ͕࣌ؒ54->23✨ ςετͷ͕͍࣌ؒ🐢 5FTU NT #VJME NT 3FQPSU T 23🤔
ͭͷ՝💥 • ςετͷ͕͍࣌ؒ🐢 • ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ʢগ͠3VCZ͔Βઢʣ • Flakyͳςετ͕ଟ͍💫
• Next.js × TypeScript ͰϑϩϯτΤϯυಈ͍͍ͯΔ • Adminը໘ͱUserը໘ͦΕͧΕ͋ΔɻϦϙδτϦ1ͭɻ • ຖճ#VJME͚ͩͰ10Ҏ্͔͔͍ͬͯΔ •
ฒྻ࣮ߦͱ͔͕ҙຯͳ͍ɻ͓ۚͰԥΕͳ͍ɻ • ςετલʹ#VJME͢Δඞཁ͕͋ΔͷͰલςετ͕͜ͷ࣮ߦ࣌ؒʹґଘ ͍ͯ͠Δ ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 94 ςετલͷBuild
Next.jsެࣜαΠτΑΓ📗 ςετલͷ#VJMEͷ͕͍࣌ؒ🥱
Next.jsެࣜαΠτΑΓ📗 ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ϏϧυͷύϑΥʔϚϯεΛ্ͤ͞ΔͨΊʹɺ /FYUKTϏϧυؒͰڞ༗͞ΕΔΩϟογϡΛOFYUDBDIFʹอଘ͠·͢ɻ ܧଓతΠϯςάϨʔγϣϯ $* ڥͰ͜ͷΩϟογϡΛ׆༻͢Δʹɺ ϏϧυؒͰΩϟογϡΛਖ਼͘͠อ࣋͢ΔΑ͏ʹɺ$*ϫʔΫϑϩʔΛߏ͢Δඞཁ ͕͋Γ·͢ɻ
Next.jsެࣜαΠτΑΓ📗 ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ϏϧυͷύϑΥʔϚϯεΛ্ͤ͞ΔͨΊʹɺ /FYUKTϏϧυؒͰڞ༗͞ΕΔΩϟογϡΛOFYUDBDIFʹอଘ͠·͢ɻ ܧଓతΠϯςάϨʔγϣϯ $* ڥͰ͜ͷΩϟογϡΛ׆༻͢Δʹɺ ϏϧυؒͰΩϟογϡΛਖ਼͘͠อ࣋͢ΔΑ͏ʹɺ$*ϫʔΫϑϩʔΛߏ͢Δඞཁ ͕͋Γ·͢ɻ .next/cacheΛΩϟογϡͯ͠Build࣌ʹ͍ճ͢
10 -> 5✨ खܰ͞: ˒˒˒ˑˑ ޮՌ: ˒˒˒˒˒
Next.jsެࣜαΠτΑΓ📗 ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ϏϧυͷύϑΥʔϚϯεΛ্ͤ͞ΔͨΊʹɺ /FYUKTϏϧυؒͰڞ༗͞ΕΔΩϟογϡΛOFYUDBDIFʹอଘ͠·͢ɻ ܧଓతΠϯςάϨʔγϣϯ $* ڥͰ͜ͷΩϟογϡΛ׆༻͢Δʹɺ ϏϧυؒͰΩϟογϡΛਖ਼͘͠อ࣋͢ΔΑ͏ʹɺ$*ϫʔΫϑϩʔΛߏ͢Δඞཁ ͕͋Γ·͢ɻ มߋͳ͍ͱ͖Buildͤͣʹɺ
Build݁ՌͷΩϟογϡΛ͍ճ͢ खܰ͞: ˒˒˒ˑˑ ޮՌ: ˒˒˒˒˒ 10 -> 5->34ඵ✨
Build͕࣌ؒ10->34ඵ✨ ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 Ϣʔβʔը໘ "ENJOը໘ ZBSOMPDLʹมߋ͕͋Δ߹ ඵ ඵ ZBSOMPDLʹมߋͳ͍͕ɺ ϑϩϯτͷίʔυʹมߋ͕͋Δ߹ ඵ
ඵ Ұมߋ͕ͳ͍߹ ඵ✨ ඵ✨
CIͷ͕࣌ؒ54->23 10✨ ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 5FTU NT #VJME T 3FQPSU T
தฤऴྃ🍻 ʢͨͿΜ13͘Β͍ܦաதʣ
ͭͷ՝💥 • ςετͷ͕͍࣌ؒ🐢 • ςετલͷ#VJMEͷ͕͍࣌ؒ🥱 ʢগ͠3VCZ͔Βઢʣ • Flakyͳςετ͕ଟ͍💫
Flakyͳςετͱʁ • ࣮ߦ݁Ռ͕ෆ҆ఆͳςετͷ͜ͱ • Flakyͳςετ͕গͳ͘ͱ30ݸҎ্͋ͬͨ • 5%ͷ֬ͰམͪΔෆ҆ఆͳςετ͕30ݸ͋Δͱɺςετ͕શͯύε ͢Δ֬21.5% Flakyͳςετ͕ଟ͍💫 103
Flakyͳςετ͕ଟ͍💫 • ࣮ߦ݁Ռ͕ෆ҆ఆͳςετͷ͜ͱ • Flakyͳςετ͕গͳ͘ͱ30ݸҎ্͋ͬͨ • 5%ͷ֬ͰམͪΔෆ҆ఆͳςετ͕30ݸ͋Δͱɺςετ͕શͯύε ͢Δ֬21.5% Flakyͳςετ͕ଟ͍💫 104
ɾࣦഊɺۉҰͰͳ͍ ɾࣦഊ͕͍ͷɺӅΕͯฆΕͯͨΓ͢Δ ɾࣦഊ͕ߴ͍ςετ͔Β͍ͯ͘͠ͱྑ͍
Flakyͳςετͷ͖߹͍ํ Flakyͳςετ͕ଟ͍💫 5FTU NT #VJME T 3FQPSU T ಓʹ͢💪
ಓʹ͢ࡍͷ େมͩͬͨ͜ͱɺͨ͜͠ͱ🛠🤖 Flakyͳςετ͕ଟ͍💫
ಓʹ͢ࡍʹେมͩͬͨ͜ͱ • CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ • CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ • FlakyΛθϩʹ͖͠Εͳ͍ Flakyͳςετ͕ଟ͍💫 107
ಓʹ͢ࡍʹେมͩͬͨ͜ͱ • CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ • CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ • FlakyΛθϩʹ͖͠Εͳ͍ Flakyͳςετ͕ଟ͍💫 108
E2E͕CI্ͰFailͨ͠Β…ϩάΛ֬ೝ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ ໘😮💨
E2E͕CI্ͰFailͨ͠Β…εΫϦʔϯγϣοτΛ֬ೝ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ ໘😮💨
Allure ReportΛಋೖ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘
• ςετ݁ՌΛྑ͍ײ͡ʹϨϙʔτ͢Δͭ • ςετͷ • ΧόϨοδ • ςετ࣌ؒ • ςετ݁Ռཤྺ
• εΫγϣͱ͔ඥ͚ΒΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 112 Allure Reportͱʁ
• bundle exec rspec --format AllureRspecFormatter • ςετͷใΛKTPOʹग़ྗ • allure
generate allure_results/* -o tmp/allure_report • ςετ݁ՌΛ)5.-ʹม • ϓϧϦΫΤετຖʹςετ݁Ռͷ)5.-Λ7FSDFMʹσϓϩΠ • ςετࣦഊ࣌ʹ7FSDFMͷ63-Λ#PU͕ίϝϯτͰڭ͑ͯ͘ΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 113 Allure Report͓ΒͤBotΛ࡞
• bundle exec rspec --format AllureRspecFormatter • ςετͷใΛKTPOʹग़ྗ • allure
generate allure_results/* -o tmp/allure_report • ςετ݁ՌΛ)5.-ʹม • ϓϧϦΫΤετຖʹςετ݁Ռͷ)5.-Λ7FSDFMʹσϓϩΠ • ςετࣦഊ࣌ʹ7FSDFMͷ63-Λ#PU͕ίϝϯτͰڭ͑ͯ͘ΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 114 Allure ReportΛಋೖ
• bundle exec rspec --format AllureRspecFormatter • ςετͷใΛKTPOʹग़ྗ • allure
generate allure_results/* -o tmp/allure_report • ςετ݁ՌΛ)5.-ʹม • ϓϧϦΫΤετຖʹςετ݁Ռͷ)5.-Λ7FSDFMʹσϓϩΠ • ςετࣦഊ࣌ʹ7FSDFMͷ63-Λ#PU͕ίϝϯτͰڭ͑ͯ͘ΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 115 Allure ReportΛಋೖ
• bundle exec rspec --format AllureRspecFormatter • ςετͷใΛKTPOʹग़ྗ • allure
generate allure_results/* -o tmp/allure_report • ςετ݁ՌΛ)5.-ʹม • ϓϧϦΫΤετຖʹςετ݁Ռͷ)5.-Λ7FSDFMʹσϓϩΠ • ςετࣦഊ࣌ʹ7FSDFMͷ63-Λ#PU͕ίϝϯτͰڭ͑ͯ͘ΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 116 Allure ReportΛಋೖ
• bundle exec rspec --format AllureRspecFormatter • ςετͷใΛKTPOʹग़ྗ • allure
generate allure_results/* -o tmp/allure_report • ςετ݁ՌΛ)5.-ʹม • ϓϧϦΫΤετຖʹςετ݁Ռͷ)5.-Λ7FSDFMʹσϓϩΠ • ςετࣦഊ࣌ʹ7FSDFMͷ63-Λ#PU͕ίϝϯτͰڭ͑ͯ͘ΕΔ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ 117 Allure ReportΛಋೖ
Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ CI͕Failͨ͠ͱ͖ ϩάεΫγϣͷ֬ೝ͕໘
Bot͕ڭ͑ͯ͘ΕΔURLΛ֬ೝ✨ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘
Allure Report͓ΒͤBotΛ࡞ Flakyͳςετ͕ଟ͍💫 - CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ खܰ͞: ˒ˑˑˑˑ ޮՌ: ˒˒˒ˑˑ
ಓʹ͢ࡍʹେมͩͬͨ͜ͱ • CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ • CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ • FlakyΛθϩʹ͖͠Εͳ͍ Flakyͳςετ͕ଟ͍💫 121
CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ ϩάεΫϦʔϯγϣοτ ͚ͩͰ'BJMݪҼ͕Θ͔Βͳ͍🤯
capybara-playwright-driverΛಋೖ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 124 capybara-playwright-driverͱʁ
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 125 capybara-playwright-driverͱʁ capybara.rb
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 126 capybara-playwright-driverͱʁ
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 127 capybara-playwright-driverͱʁ https://trace.playwright.dev/
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 128 capybara-playwright-driverͱʁ
• playwrightͱ͍͏ςετϑϨʔϜϫʔΫΛcapybara͔Β͑Δ • εΫϦʔϯγϣοτ͚ͩ͡Όͳ͘ςετ࣌ͷಈը͕ݟΒΕΔ • ։ൃऀπʔϧʹࡌͬͯΔΑ͏ͳωοτϫʔΫݟΒΕΔ • Allure Report ্ͰݟΒΕΔ
• Rails 7.1ʹऔΓࠐ·Ε͍ͯΔ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ 129 capybara-playwright-driverͱʁ
CI্Ͱ͔͠ൃੜ͠ͳ͍Flakyͷ ݪҼ͕ෆ໌ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌
ಈըͱωοτϫʔΫτϨʔε Λݟͯղܾ✨ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌
capybara-playwright-driverΛಋೖ & Allure Reportͱඥ͚ Flakyͳςετ͕ଟ͍💫 - CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ खܰ͞: ˒˒ˑˑˑ ޮՌ:
˒˒˒ˑˑ
ಓʹ͢ࡍʹେมͩͬͨ͜ͱ • CIͰςετ͕Failͨ͠ͱ͖ɺϩάεΫγϣͷ֬ೝ͕໘ • CI্Ͱ͔͠ൃੜ͠ͳ͍FlakyͷݪҼ͕ෆ໌ • FlakyΛθϩʹ͖͠Εͳ͍ Flakyͳςετ͕ଟ͍💫 133
͘͝كʹམͪΔFlakyςετ… • Ӟͷ2݄ʹམͪΔςετ • ςετதʹΛލ͍Ͱ͠·ͬͨςετ • APIϨεϙϯε͕͍ͭΑΓͳ͔ͥͨΒͯ͘མͪͨςετ Flakyͳςετ͕ଟ͍💫 134
͘͝كʹམͪΔςετCI্ͰࣗಈͰRetryͤ͞Δ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍
͘͝كʹམͪΔςετCI্ͰࣗಈͰRetryͤ͞Δ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍ 'BJMͨ͠ςετ͚ͩ࠶࣮ߦ͢Δ
͘͝كʹམͪΔςετCI্ͰࣗಈͰRetryͤ͞Δ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍ ςετࣦഊͨ͠Βɺ࣍ͷStepͷςετͰ Capybaraͷͪ࣌ؒ͘ઃఆ͢Δ
͘͝كʹམͪΔFlakyͳςετ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍
ࣦഊͨ͠ςετΛ࠶ ࣗಈͰςετ͢ΔStepΛՃͯ͠ղܾ✨ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍
ࣦഊͨ͠ςετΛ࠶ ࣗಈͰςετ͢ΔStepΛՃ Flakyͳςετ͕ଟ͍💫 - FlakyΛθϩʹ͖͠Εͳ͍ खܰ͞: ˒˒˒˒ˑ ޮՌ: ˒˒˒˒˒
~·ͱΊ~ 2024ͷࣗಈςετͷঢ়گ🔍
ςετ DBTF $*ͷ࣌ؒ ฒྻ$PSF 'MBLZςετ ݸ
͘Β͍ͷ֬Ͱ$*͕མͪΔ (JU)VC"DUJPOTͷஈ ·ͱΊ 2023ͷςετͷঢ়گ🔍
2024ͷςετͷঢ়گ🔍 ςετ DBTF DBTF $*ͷ࣌ؒ
ฒྻ$PSF ඵ🎉 ฒྻ 'MBLZςετ ݸ ͘Β͍ͷ֬Ͱ$*͕མͪΔ ݸ🎉 ͘Β͍ͷ֬Ͱ$*͕མͪΔ (JU)VC"DUJPOTͷஈ 🎉 ·ͱΊ
ͬͨ͜ͱҰཡ • CapybaraͷػೳʹͤͯSleepΛআ • LoadingΛಈతʹͭHelper࡞ͬͯSleepΛআ • test-profͷbefore_allΛͬͯσʔλ࡞Λলུ • test-profͷlet_it_beΛͬͯσʔλ࡞Λলུ •
parallel_testsͷฒྻ࣮ߦΛ׆͔ͨ͢ΊʹϑΝΠϧׂ ·ͱΊ 144
ͬͨ͜ͱҰཡ • FactoryBot.create() Ͱͳ͘ FactoryBot.build_stubbed()Λ ͏ • ͚ͳ͍͍ͯ͘ςετɺ1ͭͷ it do
~ endʹ·ͱΊΔ • ͍Βͳ͍ػೳςετআ • LoadingΛͭॲཧՄೳͳΒআ • KnapsackPro gemར༻ ·ͱΊ 145
ͬͨ͜ͱҰཡ • ͍ςετϑΝΠϧ,͍ςετ, աڈࣦഊͨ͠ςετΛμο γϡϘʔυԽ • Next.jsͷBuildΛΩϟογϡԽ • capybara-playwright-driverՃ •
AllureReportՃ • GitHubͷAllureReportͷϦϯΫBot ·ͱΊ 146
͓ർΕ༷Ͱͨ͠🍻