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
Ready for Async Rendering
Search
Sponsored
·
SiteGround - Reliable hosting with speed, security, and support you can count on.
→
koba04
April 19, 2018
Programming
1.7k
6
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Ready for Async Rendering
Scramble! #1 Frontend
https://folio.connpass.com/event/82816/
koba04
April 19, 2018
More Decks by koba04
See All by koba04
フロントエンドの現在地とこれから
koba04
10
5.4k
Standing on the shoulders of giants
koba04
0
3.1k
React/Next によるアプリケーション開発のこれから
koba04
61
19k
フロントエンド刷新をプロジェクトとして進める際に気をつけていること
koba04
3
2k
How useEvent would change our applications
koba04
1
3.3k
kintoneフロントエンド刷新によるモノリスからの脱却とその先に目指す未来
koba04
3
16k
Make it Declarative with React
koba04
0
1.9k
Ready for React in 2019
koba04
2
1.8k
Algorithms in React
koba04
14
18k
Other Decks in Programming
See All in Programming
Make SRE Operations Easier with Azure SRE Agent
kkamegawa
0
6.8k
A2UI という光を覗いてみる
satohjohn
1
140
The NotImplementedError Problem in Ruby
koic
1
840
Language Server 使ってる? 〜VSCode と Zed の場合〜 / Are you using a Language Server? ~For VS Code and Zed~
handlename
0
790
正しくソフトウェアを作る、前提を疑うための認知の視点 / doubt-premise
minodriven
21
6.7k
JJUG CCC 2026 Spring: JSpecify で実現する Kotlin フレンドリーな Java API 設計
ternbusty
1
180
dRuby over BLE
makicamel
2
380
Vite+ Unified Toolchain for the Web
naokihaba
0
320
Agentic UI
manfredsteyer
PRO
0
170
AI 輔助遺留系統現代化的經驗分享
jame2408
1
750
Snowflake Summitでの新機能 CoCo / CoWork / snowflake-summit-2026-overall-what-new-coco
tatsuhiro
1
150
Lemonade + Foundry Toolkit でお手軽アプリ開発
seosoft
1
360
Featured
See All Featured
Scaling GitHub
holman
464
140k
Amusing Abliteration
ianozsvald
1
210
Rails Girls Zürich Keynote
gr2m
96
14k
Tips & Tricks on How to Get Your First Job In Tech
honzajavorek
1
540
Why Your Marketing Sucks and What You Can Do About It - Sophie Logan
marketingsoph
0
170
Evolving SEO for Evolving Search Engines
ryanjones
0
220
Bash Introduction
62gerente
615
220k
The SEO Collaboration Effect
kristinabergwall1
1
490
Bootstrapping a Software Product
garrettdimon
PRO
307
120k
The Anti-SEO Checklist Checklist. Pubcon Cyber Week
ryanjones
0
170
How to make the Groovebox
asonas
2
2.2k
Future Trends and Review - Lecture 12 - Web Technologies (1019888BNR)
signer
PRO
0
3.6k
Transcript
3FBEZGPS"TZOD3FOEFSJOH 4DSBNCMF !LPCB
None
"HFOEB w 8IBUJT"TZOD3FOEFSJOH w -JGFDZDMF.FUIPET4USJDU.PEF w 5JNF4MJDJOH w 3FBDU4VTQFOTF
w "QQFOEJY v16.3 Changes
8IBUJT"TZOD3FOEFSJOH
w 3FBDU'JCFSJTBOVOJUPGXPSL 㲈3FBDU&MFNFOU w *UJTQPTTJCMFUPTUPQBOESFTVNFVQEBUFT 3FDBQ3FBDU'JCFS FiberA FiberB FiberD
FiberE Commit all SideEffects Idle Time Idle Time Idle Time SideEffect SideEffect Host (DOM) FiberC Render Phase Commit Phase
w 3FOEFS1IBTFʜ"TZOD w $PNNJU1IBTFʜ4ZOD 3FDBQ3FBDU'JCFS FiberA FiberB FiberD FiberE Commit
all SideEffects Idle Time Idle Time Idle Time SideEffect SideEffect Host (DOM) FiberC Async Sync
4VTQFOEBOE3FTVNF FiberA FiberB FiberA FiberC Commit Low Priority Sync Priority
Commit FiberA FiberB FiberC Low Priority Reuse Interrupt Suspend
-JGFDZDMF.FUIPET
$IBOHFTGPSMJGFDZDMFNFUIPET http://blog.koba04.com/post/2018/04/04/react-v163-changes/
w $BMMFEBU3FOEFS1IBTF w 3FUVSOBQBSUJBMTUBUFCBTFEPOOFYU1SPQT w TUBUJDHFU%FSJWFE4UBUF'SPN1SPQT static getDerivedStateFromProps(nextProps, prevState) {
if (nextProps.category !== prevState.category) { return { data: null, category: null }; } return null; } componentDidUpdate() { if (this.state.category == null) { fetchData(this.props.category).then((data) => { this.setState({category: this.props.category, data}); }); }
w $BMMFEBU$PNNJU1IBTF w 3FUVSOBTOBQTIPU BOZ CFGPSFVQEBUFUIF)PTU w UIFTOBQTIPUJTQBTTFEUPDPNQPOFOU%JE6QEBUF HFU4OBQTIPU#FGPSF6QEBUF getSnapshotBeforeUpdate()
{ return { scrollHeight: document.body.scrollHeight, scrollTop: document.body.scrollTop, }; } componentDidUpdate(prevProps, prevState, snapshot) { const {body} = document; const {scrollTop, scrollHeight} = snapshot; body.scrollTop = scrollTop + (body.scrollHeight - scrollHeight); }
https://reactjs.org/blog/2018/03/27/update-on-async-rendering.html#examples
https://github.com/facebook/react/tree/master/packages/create-subscription
4USJDU.PEF
w *EFOUJGZJOHDPNQPOFOUTVOTBGFMJGFDZDMFT w 8BSOJOHBCPVUMFHBDZTUSJOHSFG"1*VTBHF w %FUFDUJOHVOFYQFDUFETJEFF⒎FDUT 4USJDU.PEF const {StrictMode} =
React; const App = () => ( <StrictMode> <Header /> <Main /> <Footer /> </StrictMode> );
/FX$BQBCJMJUJFT
https://reactjs.org/blog/2018/03/01/sneak-peek-beyond-react-16.html
5JNF4MJDJOH
w #MPDLJOH6*UISFBEJTBOBXGVMFYQFSJFODF w 5IFSFBSFNBOZQFPQMFXIPVTFMPXQPXFSEFWJDFT w 8IZOPUEFCPVODFPSUISPUUMF 5IFBOTXFSJTʜ w SFRVFTU*EMF$BMMCBDL 5JNF4MJDJOH
<AsyncMode> <FilterInput onChange={value => { ReactDOM.flushSync(() => this.setState({value})); this.setState({data: this.filterData(value)}); }} /> </AsyncMode>
https://koba04.github.io/react-fiber-resources/examples/ Async Update Sync Update
None
https://zeit.co/blog/domains-search-web
3FBDU4VTQFOTF
https://github.com/facebook/react/pull/12279
w 3FBDU4VTQFOTFJTBGFBUVSFUPIBOEMFBTZODVQEBUFT w )5513FRVFTU w %ZOBNJD-PBEJOH w )BOEMJOHBTZODISPOPVTVQEBUFTBSFTPIBSEʜ w 4UBSU-PBEJOH
"1*4VDDFTT &SSPSʜ w .BOZMPBEJOHTQJOOFST KBOLCZBGBTUSFTQPOTF 3FBDU4VTQFOTF
3FBDU4VTQFOTF "1*XJMMCFDIBOHFE import SimpleCacheProvider from ‘simple-cache-provider’; const cache = SimpleCacheProvider.createCache();
const userFetcher = id => SimpleCacheProvider.createResource(id => fetch(`/api/users/${id}`).then(res => res.json()); )(cache, id); const User = props => { const user = userFetcher.read(props.id); return <div>{user.name}</div>; }; const Fallback = props => ( <React.Timeout ms={props.timeout}> {didExpire => didExpire ? props.placeholder : props.children} </React.Timeout> ); <Fallback placeholder=“Loading…” timeout={200}> <User id={100} /> </Fallback>
3FBDU4VTQFOTF "1*XJMMCFDIBOHFE import SimpleCacheProvider from ‘simple-cache-provider’; const cache = SimpleCacheProvider.createCache();
const routeFetcher = Component => SimpleCacheProvider.createResource(Component => import(Component).then(module => module.default); )(cache, Component); const UserPage = () => { const Component = routeFetcher.read(‘./pages/User’); return <Component />; }; const Fallback = props => ( <React.Timeout ms={props.timeout}> {didExpire => didExpire ? props.placeholder : props.children} </React.Timeout> ); <Fallback placeholder=“Loading…” timeout={1000}> <UserPage /> </Fallback>
Empty Pending Resolved Rejected read or preload throw promise return
value from cache Cache load
w 3FBDU4VTQFOTFJTCBTFEPO&SSPS#PVOEBSJFT UIPVHI XIJDIUISPXT1SPNJTFJOTUFBEPG&SSPS )PXEPFT3FBDU4VTQFOTFXPSL User Fallback Timeout throw Promise!
(suspend) timeout render with fetched Data (resume)
https://github.com/facebook/react/pull/12201
w 5IF"1*JTOPUpOBM"1* NJHIUCFDIBOHFE w *IFBSESFOEFSGVODUJPONVTUOPUIBWFBOZTJEFF⒎FDUT w 3FBDU4VTQFOTFPO443SFOEFSFS w
1SFSFOEFSBOEQSFMPBEJOHXJUIIJEEFOQSPQT w "XFTPNF8IFODBO*VTF3FBDU4VTQFOTF w .BZCFJOʜ 3FBDU4VTQFOTF
"QQFOEJY
/FX$POUFYU"1* const LangContext = React.createContext(‘en’); const ThemeContext = React.createContext(‘dark’); const
App = () => ( <LangContext.Provider value=“en”> <ThemeContext.Provider value=“dark”> <Child> <LangContext.Consumer> {lang => ( <ThemeContext.Consumer> {theme => ( <button className={theme}> {getMessage(‘click’, lang)} </button> )} </ThemeContext.Consumer> )} </LangContext.Consumer> </Child> </ThemeContext.Provider> </LangContext.Provider> );
w )BSEUPUZQFDIFDLJOH w TIPVME$PNQPOFOU6QEBUFNJHIUCSFBLUIFVQEBUF 1SPCMFNTPGMFHBDZ$POUFYU"1* GrandChild Child Parent ThemeContext Brown
-> Orange shouldComponentUpdate return false;
w 0QUJNJ[FUIFVQEBUFTGPS$POUFYUWBMVF w 3FBDUVTFTCJUXJTFPQFSBUPSJUTJOUFSOBMT 0CTFSWFE#JUT VOTUBCMF⚠ const StoreContext = React.createContext(null,
(prev, next) => { let changedBits = 0; if (prev.foo !== next.foo) changedBits |= 0b01; if (prev.bar !== next.bar) changedBits |= 0b10; return changedBits; }); // changedBits & unstable_observedBits !== 0 <StoreContext.Consumer unstable_observedBits={0b01}> {({foo}) => <div>{foo}</div> </StoreContext.Consumer> <StoreContext.Consumer unstable_observedBits={0b10}> {({bar}) => <div>{bar}</div> </StoreContext.Consumer>
https://medium.com/@koba04/a-secret-parts-of-react-new-context-api-e9506a4578aa
w 3FEVYBOE/FX$POUFYUBSFEJ⒎FSFOUMBZFST w SFBDUSFEVYNJHIUCFDIBOHFEXJUI/FX$POUFYU"1* w IUUQTHJUIVCDPNSFBDUKTSFBDUSFEVYQVMM w 8IZBSFZPVVTJOH3FEVY /FX$POUFYUBOE3FEVY
5IBOLT TQFBLFSEFDLDPNLPCB