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
Redux Middleware Wars (Japanese)
Search
Shuhei Kagawa
July 14, 2016
Technology
8
1.8k
Redux Middleware Wars (Japanese)
M3 Tech meetup! #2 ~フロントエンドの副作用~
http://m3-engineer.connpass.com/event/33802/
Shuhei Kagawa
July 14, 2016
Tweet
Share
More Decks by Shuhei Kagawa
See All by Shuhei Kagawa
Profiling Node.js apps on production
shuhei
0
830
Building a Pixel Art Editor with Elm
shuhei
1
740
Redux Middleware Wars (English)
shuhei
0
150
Draw Animated Chart on React Native
shuhei
0
8.7k
Angular 2 Offline Compiler
shuhei
0
5.4k
Weird Attractors
shuhei
0
830
Angular 2 @ JS Ojisan #6-3
shuhei
1
3k
Introduction to Angular 2
shuhei
2
140
Git の内部データ構造
shuhei
2
2k
Other Decks in Technology
See All in Technology
[Ruby] Develop a Morse Code Learning Gem & Beep from Strings
oguressive
1
150
Snowflake女子会#3 Snowpipeの良さを5分で語るよ
lana2548
0
220
新機能VPCリソースエンドポイント機能検証から得られた考察
duelist2020jp
0
210
20241214_WACATE2024冬_テスト設計技法をチョット俯瞰してみよう
kzsuzuki
3
440
開発生産性向上! 育成を「改善」と捉えるエンジニア育成戦略
shoota
1
230
KnowledgeBaseDocuments APIでベクトルインデックス管理を自動化する
iidaxs
1
260
WACATE2024冬セッション資料(ユーザビリティ)
scarletplover
0
190
プロダクト開発を加速させるためのQA文化の築き方 / How to build QA culture to accelerate product development
mii3king
1
260
あの日俺達が夢見たサーバレスアーキテクチャ/the-serverless-architecture-we-dreamed-of
tomoki10
0
430
小学3年生夏休みの自由研究「夏休みに Copilot で遊んでみた」
taichinakamura
0
150
社外コミュニティで学び社内に活かす共に学ぶプロジェクトの実践/backlogworld2024
nishiuma
0
260
.NET 9 のパフォーマンス改善
nenonaninu
0
730
Featured
See All Featured
Building a Modern Day E-commerce SEO Strategy
aleyda
38
7k
Done Done
chrislema
181
16k
RailsConf & Balkan Ruby 2019: The Past, Present, and Future of Rails at GitHub
eileencodes
132
33k
Testing 201, or: Great Expectations
jmmastey
40
7.1k
Why Our Code Smells
bkeepers
PRO
335
57k
How to Think Like a Performance Engineer
csswizardry
22
1.2k
VelocityConf: Rendering Performance Case Studies
addyosmani
326
24k
Creating an realtime collaboration tool: Agile Flush - .NET Oxford
marcduiker
26
1.9k
Bootstrapping a Software Product
garrettdimon
PRO
305
110k
Building Adaptive Systems
keathley
38
2.3k
Adopting Sorbet at Scale
ufuk
73
9.1k
JavaScript: Past, Present, and Future - NDC Porto 2020
reverentgeek
47
5.1k
Transcript
Redux Middleware Wars
Me • So$ware Engineer at M3, Inc. • ҩྍݱͰ͏γεςϜͷ։ൃ •
AngularJS, Rails, Node.js, Babel, etc. • GitHub, Qiita: @shuhei • TwiGer: @shuheikagawa • ! Ϗʔϧݕఆ 2 ڃ
Middleware ʹ͍ͭͯͦ͢ͷલʹɾɾɾ
ͦͦ Redux ͱʁ • Predictable state container for JavaScript apps
• ༧ଌՄೳͳঢ়ଶίϯςφʢ༁ʣ • ͱͱ Time traveling, hot reloading Λతͱͯ͠࡞ΒΕͨ Flux తͳԿ͔
Redux ͷ 3 ݪଇ 1. ΞϓϦͷશঢ়ଶΛҰͭͷ Object (State) ͱͯ͠อ࣋ 2.
Action ΛૹΔʢdispatchʣ͜ͱʹ ΑͬͯͷΈ State ΛมߋͰ͖Δʢͱ͍ ͏͔৽͍͠ State ͕࡞ΒΕΔʣ 3. Reducer ͱ͍͏ pure ͳؔʢಉ͡Ҿ ʹରͯ͠ৗʹಉ͡ฦΓΛฦ͢ʣʹ ΑͬͯͷΈঢ়ଶ͕มߋ͞ΕΔ reducer : (State, Action) -> State
! Pure ͳؔͱʁ • ҾͷΈʹΑͬͯฦΓ͕ܾ·Δ • ؔͷ֎ͷঢ়ଶΛมߋ͠ͳ͍ʢ෭࡞༻͕ͳ͍ʣ
! Pure ͡Όͳ͍ؔ • ࣌ʹΑͬͯฦ͕͢ҧ͏ • ฦΓ͕ͳ͍ • ҾΛมߋͯ͠͠·͏ •
ޙͰίʔϧόοΫ͕ݺΕΔ • etc.
Β͵ؒʹΞϓϦ ͷঢ়ଶ͕มΘΔ͜ ͱ͕ͳ͍
None
ͱ͍͑ɺ෭࡞༻Ͳ͏͢Δͷʁ • AJAX • local storage • cookie • ϩά
• etc.
• Reducer ͷதʹॻ͘: ແཧ • View Component ͷதʹॻ͘: ͔ͤͬ͘ঢ়ଶΛ͍ग़ͨ͠ͷ ʹɾɾɾ
• Ac4on Creator ͷதʹॻ͘: dispatch Λ͢ඞཁ͋Γ
Middleware
Redux Middleware ͱ • dispatch ͷલޙʹॲཧΛڬΉ • Action Λड͚ͯɺΰχϣΰχϣͰ͖ Δ
• Action ΛͪΐͬͱΒͤͯૹΔ • ผͷ Action ʹஔ͖͑Δ • ඇಉظॲཧΛߦ͍ɺ݁ՌΛ Action ͱͯ͠ૹΔ • e.g. WSGI, Rack, Express, Koa, etc.
ྫ: ͳʹ͠ͳ͍ ड͚औͬͨ Ac$on Λͦͷ··࣍ͷ middleware ʹ͛Δ const passthrough =
store => next => action => { return next(action); };
ྫ: ϩάΛग़ྗ ࣍ͷ middleware ʹ ac+on Λ͛ΔʢnextʣલޙͰϩάΛग़ྗ const logger =
store => next => action => { console.log('prev state', store.getState()); console.log('action', action); const returnValue = next(action); console.log('next state', store.getState()); return returnValue; };
ྫ: Promise ͷ݁ՌΛͭ const promise = store => next =>
action => { if (typeof action.then === 'function') { return action.then(store.dispatch); } else { return next(action); } }; function fetchPosts() { return fetch('/posts').then(res => res.json()) .then(posts => ({ type: 'POSTS_FETCHED', posts })); } dispatch(fetchPosts);
ࠓճඇಉظॲཧΛߦ͏ Middleware ʹয
΄͍͠ͷ • ! ςετͷ͢͠͞ʢϞοΫແ͠ͰςετͰ͖Δͱ࠷ߴʣ • " ۭ࣌Λ͑Δʢthro'ling, debouncingʣ • #
ϩδοΫͷڽू • ✨ ։ൃͷ׆ൃ͞
ඇಉظॲཧΛߦ͏ Middleware ಠஅͱภݟʹΑΓ... | ----------------- | ---- | --------- |
---- | ---- | ---- | ---- | | name | star | from | test | time | cohe | acti | | ----------------- | ---- | --------- | ---- | ---- | ---- | ---- | | redux-thunk | 2392 | '15/07/13 | C | C | B | A | | redux-promise | 864 | '15/07/02 | - | C | C | C | | redux-saga | 3172 | '15/11/30 | B | A | A | A | | redux-loop | 641 | '16/01/06 | A | C | B | C | | redux-observable | 634 | '16/02/16 | C | A | B | A | | ----------------- | ---- | --------- | ---- | ---- | ---- | ---- | ⭐ ͷ 2016/7/5 ௐ
redux-thunk ⭐2392 Ac#on ͱͯؔ͠ʢthunkʣ͕དྷͨΒɺͦΕΛ࣮ߦ͢ΔʢҾʹ dispatch ͱ getStateʣ const fetchBeers =
() => (dispatch, getState) => { return fetch('/beers') .then(res => res.json()) .then(items => dispatch('FETCH_BEERS_SUCCEEDED', items)) .catch(error => dispatch('FETCH_BEERS_FAILED', error)); }; dispatch(fetchBeers());
redux-thunk ⭐2392 • ! ϞοΫ͠ͳ͍ͱςετ͕ॻ͚ͳ͍ • " Ac%on ΛҰ͔ͭͮͭ͠ड͚ΒΕͳ͍ͷͰɺdebounce ͳͲ͕
͍͠ • # ΄Ͳ΄ͲʹෳࡶͳϩδοΫॻ͚Δ • ✨ ΄Ͳ΄Ͳʹϝϯς͞Ε͍ͯΔɻͦͦ 13 ߦ͔͠ͳ͍ • ࢀߟ: How to dispatch a Redux ac%on with a %meout?
redux-promise ⭐864 FSA (Flux Standard Ac/on) ͷ payload ͷ promise
Λղܾ͠ɺ Ac/on ͱͯ͠ૹΓͯ͘͠ΕΔ function fetchItems() { const promise = fetch('/items').then(res => res.json()); return { type: 'FETCH_ITEMS', payload: promise }; } dispatch(fetchItems());
redux-promise ⭐864 • ! γϯϓϧͳͷͰɺͦ͜·Ͱςετ͠ͳͯ͘ྑͦ͞͏ • " debounce ͳͲͰ͖ͳ͍ •
# ෳࡶͳϩδοΫॻ͚ͳ͍ • ✨ 4 ϲ݄ఔϝϯς͞Εͯͳ͍ɻ25 ߦ͚͕ͩͩɾɾɾ • Τϥʔॲཧͷൺֱతॏཁͦ͏ͳ MR ͕Ϛʔδ͞Ε͕ͨϦϦʔ ε͞Ε͍ͯͳ͍
redux-saga ⭐3172 Saga ͱݺΕΔ generator (saga) Ͱ෭࡞༻Λ͏ॲཧΛهड़ function* fetchBeer(action) {
try { const beers = yield call(fetchBeer, action.id); yield put({ type: 'FETCH_BEER_SUCCEEDED', payload: beers }); } catch (error) { yield put({ type: 'FETCH_BEER_FAILED', error }); } } function* watchFetchBeer() { yield* takeEvery('FETCH_BEER', fetchBeer); }
redux-saga ⭐3172 • ! ςετ͕͍͢͠ʂʂʂ • ෭࡞༻ϦΫΤετΛ yield ͯ͠ɺmiddleware ʹ࣮ߦͯ͠
Β͍ɺ݁ՌΛड͚औΔ • ࣗ pure ͳ··ෳࡶͳඇಉظॲཧ͕ॻ͚Δ • ৄ͘͠ @kuy ͞Μͷ͓Ͱɾɾɾ
redux-loop (store enhancer) ⭐641 Elm Λਅࣅͨ APIɻreducer ͕ state ͚ͩͰͳ͘
Effects ฦ͢ function beers(state = [], action) { switch (action.type) { case 'FETCH_BEERS': return loop(state, Effects.promise(fetchBeers)); case 'FETCH_BEERS_SUCCEEDED': return action.payload; default: return state; } }
redux-loop (store enhancer) ⭐641 • ! ϞοΫͳ͠ͰςετͰ͖Δ • Effects ͨͩͷ
Objectɻ࣮ߦ͢Δ·Ͱ෭࡞༻ى͖ͳ͍ • " debounce ͳͲͰ͖ͳͦ͞͏ • # Effects ΛΈ߹ΘͤΔ͜ͱ͕Ͱ͖Δ • ✨ 3 ϲ݄΄Ͳϝϯς͞Ε͍ͯͳ͍ɻ࡞ऀ͕ Elm ͔͠ॻ͔ͳ͘ ͳͬͯ͠·ͬͨʁ
redux-observable ⭐ 634 reducer ͷޙͰ Action Λड͚ͯ Action Λग़ྗ͢Δ Observable
Λฦ͢ function beerEpic(action$, store) { const beers$ = action$.ofType('FETCH_ITEMS') .mergeMap(() => Observable.fromPromise(fetchBeers())) .map(beers => ({ type: 'FETCH_BEERS_SUCCEEDED', payload: beers })); return Observable.merge( beers$, something$ ); }
redux-observable ⭐ 634 • ! ϞοΫ͠ͳ͍ͱςετͰ͖ͳ͍ • " Rx ͷڧྗͳ
operator Ͱ༰қʹۭ࣌Λ੍ͤΔ • # redux-saga తͳ background processor style ʹਐԽ • ෳࡶͳॲཧॻ͚Δ • ✨ ݱࡏ։ൃதɻͱͯγϯϓϧ • Rx ΩϚΔͱؾ͍͍࣋ͪʢݸਓͷײʣ
τϨϯυʢʁʣ • σʔλͱͯ͠ͷ෭࡞༻ʢsaga, loop, Cycle.jsʣ • ෭࡞༻ϦΫΤετΛ middleware ͕ॲཧ͢Δ •
։ൃऀ͕ॻ͘ϩδοΫ͕៉ྷʹอͯΔ • Background processor ελΠϧʢsaga, observable, chooʣ • reducer ͷલͰͳ͘ޙͰ Action Λड͚Δ
࠙ձͰ͍Ζ͍Ζڭ͑ͯԼ͍͞ʂ
Thanks!
Credits • Chart of Redux from h0p:/ /www.bebe0erdeveloper.com/coding/ ge=ng-started-react-redux.html