Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
React.js for WordPress Developers
Search
Nikolay Bachiyski
April 16, 2016
Programming
300
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
React.js for WordPress Developers
Nikolay Bachiyski
April 16, 2016
More Decks by Nikolay Bachiyski
See All by Nikolay Bachiyski
Building Calypso-like Applications
nb
3
880
Else Considered Harmful
nb
2
1.1k
On Learning
nb
2
830
WordPress: To OOP or not to OOP
nb
4
8.2k
On Creeds and Manifestos
nb
2
240
Welcome to the Chaos – The Distributed Workplace
nb
3
240
To a thousand servers and beyond: scaling a massive PHP application
nb
3
1.6k
Взимане на продуктови решения (Making product decisions)
nb
0
170
Other Decks in Programming
See All in Programming
Androidだけじゃない、DroidKaigiで広がった私の技術スタック
akkeylab
0
100
難しいけど、読めた。- OSSの入口に立った話。
sts11142
0
130
[Rails World 2026] Durable orchestration on Rails: from continuation to workflow
palkan
1
390
AI時代のコードレビューは人に向けるな、仕組みに向けろ
texmeijin
5
2.9k
ゲームコントローラやキーボードのファームウェアをSwiftで書く
kishikawakatsumi
1
270
選挙速報を多くのユーザーへ 届ける Live Activities 設計
hamayokokuririn
0
190
速く作れる。その次は、速く確かめられる開発へ 〜AIネイティブ開発を支える、Shift Down〜 / Can build fast. Next, moving to development where we can verify fast.
rkaga
8
5.2k
JRuby: Past, Present, and Future
headius
0
210
FreeBSDでZabbixを動かす
kenkino
0
340
Vue Fes Japan 2026 タイムテーブル徹底解説
448jp
1
570
一人だけ、Kiroが静止する日
hideg
0
140
カツオ、ご期待ください
suneo3476
0
120
Featured
See All Featured
[Rails World 2026] Durable orchestration on Rails: from continuation to workflow
palkan
1
390
Why You Should Never Use an ORM
jnunemaker
PRO
61
10k
Leveraging Curiosity to Care for An Aging Population
cassininazir
1
520
How to build an LLM SEO readiness audit: a practical framework
nmsamuel
2
930
How to Build an AI Search Optimization Roadmap - Criteria and Steps to Take #SEOIRL
aleyda
1
2.2k
JavaScript: Past, Present, and Future - NDC Porto 2020
reverentgeek
52
6.1k
Understanding Cognitive Biases in Performance Measurement
bluesmoon
32
3k
What Being in a Rock Band Can Teach Us About Real World SEO
427marketing
0
1.1k
Building Applications with DynamoDB
mza
96
7.2k
The B2B funnel & how to create a winning content strategy
katarinadahlin
PRO
1
550
Evolution of real-time – Irina Nazarova, EuRuKo, 2024
irinanazarova
9
1.6k
Thoughts on Productivity
jonyablonski
76
5.4k
Transcript
N I KO L AY B A C H I
Y S K I , A U TO M AT T I C , W O R D C A M P H E L S I N K I , A P R I L 1 6 , 2 0 1 6
None
A U TO M AT T I C
A U TO M AT T I C E X
T R A P O L AT E . M E
A U TO M AT T I C E X
T R A P O L AT E . M E @ N I KO L AY B
R E S T A P I
R E S T A P I CALYPSO
R E S T A P I ↓ S I
N G L E - PA G E A P P S
W H Y ?
None
FA S T E R
None
M O R E E N G A G I
N G
None
None
C H A N G E L E T '
S TA L K A B O U T
None
None
None
None
None
None
S TAT E L E T ' S TA L
K A B O U T
None
None
None
C L A S S I C V S .
S I N G L E - PA G E A P P S
C L A S S I C
None
None
C H A N G E 㱺 R E F
R E S H C L A S S I C
C H A N G E 㱺 S I N
G L E - PA G E
C H A N G E 㱺 S I N
G L E - PA G E
None
None
U I L I B R A RY
N OT A F R A M E W O
R K
U I L I B R A RY
const Post = React.createClass( { render() { return ( <div
className="post"> <p className="content"> { this.props.post.content } </p> <PostMeta post={ this.props.post } /> </div> ); } } );
const Post = React.createClass( { render() { return ( <div
className="post"> <p className="content"> { this.props.post.content } </p> <PostMeta post={ this.props.post } /> </div> ); } } );
const Post = React.createClass( { render() { return ( <div
className="post"> <p className="content"> { this.props.post.content } </p> <PostMeta post={ this.props.post } /> </div> ); } } ); J SX
const Post = React.createClass( { function render() { return (
React.DOM.div( {className: 'post'}, [ React.DOM.p( null, this.props.post.content ), PostMeta( {post: this.props.post} ) ); ); } } );
const Post = React.createClass( { render() { return ( <div
className="post"> <p className="content"> { this.props.post.content } </p> <PostMeta post={ this.props.post } /> </div> ); } } );
const PostMeta = React.createClass( { … } );
const Post = React.createClass( { render() { return ( <div
className="post"> <p className="content"> { this.props.post.content } </p> <PostMeta post={ this.props.post } /> </div> ); } } );
const PostMeta = React.createClass( { getInitialState() { return { hidden:
true }; }, onToggle() { this.setState( { hidden: ! this.state.hidden } ); }, render() { return ( <div className="meta"> { this.props.post.author } <button onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); } } );
const PostMeta = React.createClass( { getInitialState() { return { hidden:
true }; }, onToggle() { this.setState( { hidden: ! this.state.hidden } ); }, render() { return ( <div className="meta"> { this.props.post.author } <button onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); } } );
const PostMeta = React.createClass( { getInitialState() { return { hidden:
true }; }, onToggle() { this.setState( { hidden: ! this.state.hidden } ); }, render() { return ( <div className="meta"> { this.props.post.author } <button onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); } } );
const PostMeta = React.createClass( { getInitialState() { return { hidden:
true }; }, onToggle() { this.setState( { hidden: ! this.state.hidden } ); }, render() { return ( <div className="meta"> { this.props.post.author } <button onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); } } );
const PostMeta = React.createClass( { getInitialState() { return { hidden:
true }; }, onToggle() { this.setState( { hidden: ! this.state.hidden } ); }, render() { return ( <div className="meta"> { this.props.post.author } <button onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); } } ); R E - R E N D E RS
C O M P O N E N T S
L E T ' S TA L K A B I T M O R E A B O U T
C O M P O S A B L E
<MasterBar> <UserGreeting user="…"> <Avatar login={ this.props.user.login } /> Howdy, {
this.props.user.nickname } <LogOutLink id={ this.props.user.id } /> </UserGreeting> </MasterBar>
B U I L D I N G B LO
C KS O F O U R A P P L I C AT I O N
<MasterBar /> <MastHead /> <Navigation active="archive" /> <Posts date="2015-04-01" author="crumb">
<Post> … </Post> <Post> … </Post> … </Posts>
const Post = React.createClass( { … <p class="content"> { this.props.post.content}
</p> <PostMeta post="…" /> …
None
T E S TA B L E
P R E V E N T S XS S
<p>{ this.props.content }</p> <img src="javascript:alert('XSS');"> <img src="javascript:alert('XSS');">
<p dangerouslySetInnerHTML={{ __html: this.props.content }} />
N OT T E M P L AT E S
<div class="posts"> {{#each posts}} <div class="post"> {{#if author}} </div> {{/each}}
{{^posts}} Not Found {{/posts}} </div>
R E U S A B L E
<Comment> <Avatar email={ this.props.comment.author.email } /> … </Comment>
<PostMeta> <Avatar email={ this.props.comment.author.email} /> … </PostMeta>
AV ATA R = I M G + H O
V E R J S
W A I T!
K E E P LO G I C A N
D M A R K U P … A P O P U L A R B E S T P R A C T I C E S A Y S …
… S E PA R AT E !
S E PA R AT I O N O F
C O N C E R N S I S G O O D, R I G H T ?
W H E N D O W E N E
E D A N E V E N T H A N D L E R W I T H O U T T H E D O M E L E M E N T I T I S B O U N D TO ?
W H E N D O W E N E
E D A N E V E N T H A N D L E R W I T H O U T T H E D O M E L E M E N T I T I S B O U N D TO ? onClick() <button>
W H E N D O W E N E
E D A D O M E L E M E N T W I T H O U T T H E E V E N T H A N D L E R S F O R I T S A C T I O N S ? onClick() <button>
H TM L
D I S P L AY LO G I C
T H E S A M E C O N
C E R N
H TM L J S
H TM L
D I S P L AY LO G I C
T H E S A M E C O N
C E R N
None
None
None
R E - R E N D E R I
N G
None
None
None
None
V I R T U A L D O M
0 . R U N r e n d e
r ( ) O N E V E RY U P D A T E
1 . D I F F W I T H
P R E V I O U S T R E E O N E V E RY U P D A T E
http://calendar.perfplanet.com/2013/diff/
2 . CO M P U T E M I
N I M U M S E T O F D O M C H A N G E S O N E V E RY U P D A T E
3 . B ATC H - E X E C
U T E A L L D O M U P D AT E S O N E V E RY U P D A T E
V I R T U A L D O M
: N OT O N LY S P E E D!
S E R V E R-S I D E R
E N D E R I N G
S V G , V M L , C A
N V A S
R U N N I N G I N A
W E B W O R K E R
D E C L A R AT I V E
None
None
sample
M A G I C!
None
render() { return ( <div className="meta"> { this.props.post.author } <button
onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); }
render() { return ( <div className="meta"> { this.props.post.author } <button
onClick={ this.onToggle }> { this.state.hidden ? 'More' : 'Hide' } </button> ( this.state.hidden ? <p>…extra meta…</p> : null ) </div> ); }
None
None
RO U T E R + S TAT E http://redux.js.org
https://github.com/reactjs/react-router https://egghead.io
N OT A F R A M E W O
R K
A RC H I T E C T U R
E
http:/ /github.com/Automattic/wp-calypso
L E T ' S C H AT
S U M M A RY
C O M P O N E N T S
, N OT T E M P L AT E S
R E - R E N D E R ,
D O N ' T TO U C H T H E D O M
V I R T U A L D O M
I S S I M P L E , FA S T, F U N L E T ' S TA L K A B O U T
C O N T R I B U TO R
D AY!
Q U E S T I O N S ?
@ N I KO L AY B