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
pixiv SketchのSSRの話
Search
geta6
April 11, 2017
Technology
10
4.2k
pixiv SketchのSSRの話
pixiv SketchでSSRしている感じの話です
geta6
April 11, 2017
Tweet
Share
More Decks by geta6
See All by geta6
mastodonのnodeのはなし
geta6
0
3.1k
ReactとFluxのこと
geta6
166
64k
What is CoffeeScript
geta6
8
890
Other Decks in Technology
See All in Technology
Perlの生きのこり - YAPC::Fukuoka 2025
kfly8
0
670
なぜThrottleではなくDebounceだったのか? 700並列リクエストと戦うサーバーサイド実装のすべて
yoshiori
13
4.9k
Moto: Latent Motion Token as the Bridging Language for Learning Robot Manipulation from Videos
peisuke
0
160
明日から真似してOk!NOT A HOTELで実践している入社手続きの自動化
nkajihara
1
870
PostgreSQL で列データ”ファイル”を利用する ~Arrow/Parquet を統合したデータベースの作成~
kaigai
0
140
ステートレスなLLMでステートフルなAI agentを作る - YAPC::Fukuoka 2025
gfx
8
1.4k
プロダクト負債と歩む持続可能なサービスを育てるための挑戦
sansantech
PRO
1
640
雲勉LT_Amazon Bedrock AgentCoreを知りAIエージェントに入門しよう!
ymae
2
180
グローバルなコンパウンド戦略を支えるモジュラーモノリスとドメイン駆動設計
kawauso
3
6k
ABEMAのCM配信を支えるスケーラブルな分散カウンタの実装
hono0130
4
1k
事業状況で変化する最適解。進化し続ける開発組織とアーキテクチャ
caddi_eng
1
4.5k
AIと自動化がもたらす業務効率化の実例: 反社チェック等の調査・業務プロセス自動化
enpipi
0
750
Featured
See All Featured
ピンチをチャンスに:未来をつくるプロダクトロードマップ #pmconf2020
aki_iinuma
127
54k
Chrome DevTools: State of the Union 2024 - Debugging React & Beyond
addyosmani
9
980
Fashionably flexible responsive web design (full day workshop)
malarkey
407
66k
The Art of Delivering Value - GDevCon NA Keynote
reverentgeek
16
1.8k
How to train your dragon (web standard)
notwaldorf
97
6.4k
Dealing with People You Can't Stand - Big Design 2015
cassininazir
367
27k
StorybookのUI Testing Handbookを読んだ
zakiyama
31
6.3k
jQuery: Nuts, Bolts and Bling
dougneiner
65
8k
It's Worth the Effort
3n
187
28k
Building Better People: How to give real-time feedback that sticks.
wjessup
370
20k
Documentation Writing (for coders)
carmenintech
76
5.1k
The Language of Interfaces
destraynor
162
25k
Transcript
None
௮͚͜Μͩ443ͷ αʔόʔαΠυϨϯμϦϯά
w ໊લɿ͛ͨ w ৬ۀɿҰൠϊʔϚϧΤϯδχΞ w QJYJW4LFUDIͰ8FCଆͷ࣮શൠͨ͠Γϔϧϓͯ͠ ͘ΕΔਓͷհޢΛͨ͠Γ͍ͯ͠·͢ HFUB
443ͬͯͳʹΑ w αʔόʔαΠυϨϯμϦϯάͷ͜ͱ w ͬ͘͟Γݴ͏ͱ w 41"ͷॳճϩʔυ͍ͨ͘͠ w KTͰίϯςϯπߏங͠ऴΘͬͨঢ়ଶΛαʔόʔ αΠυͰ࡞ͬͯग़ͪ͠Ό͑͘ͳΔ͡ΌΜʂͦ
ͷ··ಉ͡ίʔυ͍ճͤΔ͠ఱ࠽ʂ w ͱ͍͏ײ͡ͷΞϨ
͢͜ͱϦετ w TLFUDIͷΞʔΩςΫνϟʢ֓આʣ w 443ͬͯ۩ମతʹͲ͏Δͷ w DTTͲ͏ͯ͠Δͷ w ͳΜͰ443ʹͳͬͨͷ w
σϝϦοτͱϝϦοτ w ͦͷͨ
ΞʔΩςΫνϟ
ΞʔΩςΫνϟ Web Browser pixiv Sketch API rails iOS Android iOS
app Android app node.js javascript ࠷ۙͨ·ʹݟ͔͚Δߏ͚ͩͲɺͬͯΔͱ͜গͳͦ͏
ΞʔΩςΫνϟ Web Browser pixiv Sketch API rails iOS Android iOS
app Android app node.js javascript ΅͘ͷ୲
Web Browser pixiv Sketch API rails node.js javascript ΞʔΩςΫνϟ express
React + Fluxible
Web Browser pixiv Sketch API rails node.js javascript ΞʔΩςΫνϟ SSR
React SharedCode XHR HTTP viewͳ͠ɺjson͚ͩ
Web Browser pixiv Sketch API rails node.js javascript ΞʔΩςΫνϟ MCͷೄுΓ
VͷೄுΓ αʔόʔ͖ͷڊେͳSPA
3FOEFSFS w OPEFαʔόʔ SFOEFSFS ϏδωεϩδοΫηο γϣϯػߏΛҰ͍࣋ͬͯͳ͍ w "1*͔Β͞ΕͨσʔλΛݩʹɺϒϥβͱಉ͡ ίʔυͰ)5.-Λߏஙͯ͠ϨϯμϦϯά w
αʔόʔαΠυͰ"1*ϦΫΤετ)551 w $PPLJFϔομΛαʔόʔͷ)551ϦΫΤελʔʹ ηοτͯ͠ೝূঢ়ଶΛදݱ
3FOEFSFS w ؆୯ʹݴ͏ͱ.7$ͷ.$͕SBJMTͰ7͕OPEF w .$ͱ7ͷؒʹΞʔΩςΫνϟͷน͕ଘࡏ͢Δʢݴ ޠɾ'8ɾΠϯελϯε͕ҧ͏ʣͷͰɺޓ͍Λ৵ ൜Ͱ͖ͳ͍
3FOEFSFS w 6*ͷ͜ͱ͚ͩΛߟ͍͑ͯΕ͍͍ɺϩδοΫʹབྷΉ ෳࡶͳॲཧ"1*ʹͿΜ͛ͯɺ͓͔͔ͬͨ͠ΒYY ͔YY͕ฦͬͯ͘ΔͷͰΑ͠ͳʹमਖ਼ w ෦ใಛݖతʹΞΫηε͢Δखஈ͕ଘࡏ͠ͳ͍ ͷͰɺOPEF࣮ͷΤϯόά͕ηΩϡϦςΟϦεΫ ʹܨ͕ΔՄೳੑ͕͍ "1*͕ਖ਼͍͠ͱԾఆͯ͠
3FOEFSFS Web Browser pixiv Sketch API rails node.js javascript ӽ͑ΒΕͳ͍น
SSR͢ΔͱMCͱV ͚͟ΔΛಘ͘ͳΔ
3FOEFSFS w .7$ڲਖ਼Ϊϒε w ͲΕ͚ͩٸ͍Ͱ͍ͯ಄ͷ͓͔͍͠7JFXίʔυ ͕ॻ͚ͳ͍ɺෛ࠴ઈର࡞Βͳ͍Ϛϯ w 443͍͍ͧ
۩ମతʹͲ͏Μͷʁ
443ग़ྗͷΠϝʔδ w %0$5:1&Ҏ֎ͷ)5.-Λશͯ3FBDUͰߏங w BDUJPOΛୟ͍ͯίϯςϯπදࣔʹඞཁͳTUPSF σʔλΛऩू w 3FBDU%0.SFOEFS5P4UBUJD.BSLVQΛར༻ͯ͠ %0.ΛTUSJOHʹ͢Δɺ͍ͭ͜ʹ%0$5:1&Λͬ͘ ͚ͭͯFYQSFTT͔ΒSFTTFOE͢Δ͚ͩ
w ͔ΜͨΜʂʂ
443ग़ྗͷΠϝʔδ const app = new Fluxible({ /* shared app root
component, stores */ }); const srv = express(); srv.use((req, res) => { req.context = app.createContext(); /* ͍Ζ͍Ζ४උ͢Δ (APIΛfetchͨ͠Γͯ͠ɺfluxΛճ͢) */ const react = React.createElement(Html, { context: req.context }); const html = ReactDOM.renderToStaticMarkup(react); res.send(`<!doctype html>${html}`); }); ͜͜Ͱڞ௨ίʔυ Λ͢ html͕ϧʔτͷ component ͔ΜͨΜʂʂ
express (1 request) 443ग़ྗͷΠϝʔδ req Flux Context res React Flux
Context ReactDOM store store css React (html)
express (1 request) 443ग़ྗͷΠϝʔδ req Flux Context res React Flux
Context ReactDOM store store css React (html) shared shared server code
JTPNPSQIJDTUPSF w TUPSFͷσʔλTFSWFS͔ΒDMJFOUҙࣝతʹͯ͠ ͋͛ͳ͍ͱ͍͚ͳ͍ w TUPSFͷঢ়ଶTFSJBMJ[Fͨ͠KTσʔλͱͯ͠ςϯϓ Ϩʔτ )UNM$PNQPOFOU ͔ΒϖʔδʹຒΊࠐΉ w
DMJFOUͷॳظԽ࣌ʹ͜ΕΛೖखͯ͠TUPSFͷঢ়ଶΛ ෮چͤ͞Δ
JTPNPSQIJDTUPSF const app = new Fluxible({ /* shared app root
component, stores */ }); const srv = express(); srv.use((req, res) => { req.context = app.createContext(); /* ͍Ζ͍Ζ४උ͢Δ (APIΛfetchͨ͠Γͯ͠ɺfluxΛճ͢) */ const dehydrated = `window.dehydrated=${serialize(app.dehydrate(req.context))}`; const react = React.createElement(Html, { context, dehydrated }); const html = ReactDOM.renderToStaticMarkup(react); res.send(`<!doctype html>${html}`); }); serializeͯ͢͠
JTPNPSQIJDDTT w XFCQBDLΛ༻ͯ͠DTTΛఏڙ͢ΔGVODUJPOͱͯ͠ USBOTQJMF͓ͯ͘͠ʢLSJBTPGUJTPNPSQIJDTUZMF MPBEFSʣ w $PNQPOFOUϚϯτ࣌ʹ͜ͷϝιουΛݺΜͰɺ ͕ࣗඞཁͱ͢ΔTUZMFΛϒϥβʹఏڙ͢Δ
JTPNPSQIJDDTT w DMJFOUͱTFSWFSͰDTTͷॲཧํ๏Λม͑Δ w TFSWFSͰDTTΛTUSJOHͱͯ͠ಘΔGVODUJPOΛ࣮ߦɺ BSSBZʹTUSJOHΛQVTI͓͍ͯͯ͠ϨϯμϦϯά࣌ʹ TUZMFλάʹల։͢Δ w DMJFOUͰTUZMFΛIFBEʹJOTFSU͢Δ%0.ૢ ࡞͖GVODUJPOΛ࣮ߦ
JTPNPSQIJDDTT const app = new Fluxible({ /* shared app root
component, stores */ }); const srv = express(); srv.use((req, res) => { req.context = app.createContext(); /* ͍Ζ͍Ζ४උ͢Δ (APIΛfetchͨ͠Γͯ͠ɺfluxΛճ͢) */ const context = req.context.getComponentContext(); const styles = []; context.insertCss = (s) => styles.push(s._getCss()); const dehydrated = `window.dehydrated=${serialize(app.dehydrate(req.context))}`; const react = React.createElement(Html, { context, dehydrated, styles }); res.send(`<!doctype html>${html}`); }); ReactContextͰpush ͢ΔϝιουΛ͢
)UNM$PNQPOFOU w EBOHFSPVTMZ4FU*OOFS)5.-Λͬͯ͞ΕͨTUZMF TFSJBMJ[F͞ΕͨTUPSFσʔλΛΨϯΨϯຒΊࠐΉ w DMJFOU༻ͷॳظԽTDSJQUͰςϯϓϨʔτͱͯ͠ຒΊࠐ ·Εͨ͜ΕΒΛೖख͠ɺDMJFOUଆͷΞϓϦέʔγϣ ϯΛαʔόʔͱಉ͡ঢ়ଶʹ෮چ͢Δ
express (1 request) 443ग़ྗͷΠϝʔδ req Flux Context res React Flux
Context ReactDOM store store css React (html) serialize ArrayPush render toStaticMarkup res.send
DTTͷ͜ͱৄ͘͠
˺8FC$PNQPOFOUT w 4LFUDI8FC൛ͷ$PNQPOFOUઓུ w 3FBDU$PNQPOFOUͷKT࣮ɾDTTείʔϓ͕ࣗ ͷ֎ӨڹΛٴ΅͞ͳ͍Α͏ʹ࣮ɾઃܭ͢Δ w DTTXFCQBDLΛ༻ͯ͠KTʹแɺίϯϙʔωϯ τ୯ҐͰهड़͠ίϯϙʔωϯτࣗʹཧͤ͞Δ w
LSJBTPGUJTPNPSQIJDTUZMFMPBEFSࢀর
˺8FC$PNQPOFOUT w DPNQPOFOU8JMM.PVOUͰDTTΛϚϯτ͠ɺ DPNQPOFOU8JMM6ONPVOUͰDTTΛΞϯϚϯτ͢Δ w ϚϯλʔɾΞϯϚϯλʔ෦ʹΧϯλʔ Λ͍࣋ͬͯΔ w Ϛϯλʔʮطʹࣗͱಉ͡$PNQPOFOU͕ଘ ࡏ͍ͯ͠ΕʯϚϯτ͠ͳ͍
w ΞϯϚϯλʔʮ·ͩࣗͱಉ͡$PNQPOFOU ͕ଘࡏ͍ͯ͠ΕʯΞϯϚϯτ͠ͳ͍
ίϯϙʔωϯτߏ - Component/ `- package.json // { "main": "Component.jsx" }
`- Component.jsx // component `- Component.styl // stylesheet for component σΟϨΫτϦΛimportͨ࣌͠ʹ mainͷΛࢀরͯ͘͠ΕΔ
$PNQPOFOUKTY import React, { Component } from 'react'; import {
withStyle } from '../../utils/Decorator'; @withStyle(require('./Component.styl')) export default class Component extends Component { static displayName = 'Component'; componentDidMount = () => { console.log('mounted'); }; render = () => ( <div id='Component'> <div id='ComponentBody'> <span>component content</span> </div> </div> ); } ޙड़ ίϯϙʔωϯτ໊ͱಉ͡ id͔classΛRootʹऔΔ ※ transform-decorators-legacy
$PNQPOFOUTUZM #Component &Body box-sizing border-box margin 0 auto padding 0
20px max-width 600px width 100% ϑΝΠϧ͋ͨΓ Root1ݸͷϧʔϧ
4UZMF%FDPSBUPS import noop from 'lodash/noop'; import React, { Component, PropTypes
} from 'react'; export const withStyleDecorator = (style) => (ComposedComponent) => ( class WithStyle extends Component { static displayName = `withStyle(${ComposedComponent.displayName})`; static contextTypes = { insertCss: PropTypes.func.isRequired, }; constructor(props, context) { super(props, context); this.removeCss = style ? this.context.insertCss(style) : noop; } componentWillUnmount = () => { this.removeCss && setTimeout(this.removeCss, 0); }; render = () => ( <ComposedComponent {...this.props} /> ); } ); isomorphic-style-loader ͔Βఏڙ͞ΕΔϚϯλʔ
4UZMFTIFFU3VMF w ίϯϙʔωϯτ໊ͱϧʔτͷJEDMBTT໊ΛҰகͤ͞ ΔͱɺϑΝΠϧγεςϜͷ੍্͓ͳ໊͡લͷ 3PPU&MFNFOU࡞Ͱ͖ͳ͘ͳΔ w ໊લ͚ͷϧʔϧΛ౷Ұ͢Δ͚ͩͳͷͰDTTNPEVMF Λಋೖ͢ΔΑΓखܰ
443Λબͨ͠ཧ༝
8FCͷେ·͔ͳมભ w ։ൃ։࢝ νʔϜϝϯόʔਓ w ϦϦʔε w
υϩʔػೳWϦϦʔε 4NPPUI-JOF w 8FCϦϑΝΫλϦϯά w υϩʔػೳWϦϦʔε 8FC(-൛
w ϦϦʔε͔Βݱࡏ·ͰΞʔΩςΫνϟʹมߋͳ͠ w αʔϏεϦϦʔε͔ΒҰ؏ͯ͠αʔόछߏɺ ʮػೳՃʯͱʮ࠷దԽʯͷΈΛ࣮ࢪ w ϦϑΝΫλ3FBDUWରԠʹਵ͢Δ$PNQPOFOU ࠷దԽɾTUPSFपΓͷϝϞϦར༻࠷దԽɾ&4 ͷै͕ओͳλʔήοτ w
αʔϏεϦϦʔε࣌ʹཁ݅ʹ߹க͢Δʮਖ਼ղʯͷΞʔ ΩςΫνϟΛબ͢Δ͜ͱ͕Ͱ͖ͨ
443ΛܾΊͨϑϩʔ
443ΛܾΊͨϑϩʔ w Ұ൪࠷ॳOPEFͰϓϩτλΠϐϯάͨ͠ w ࣌3FBDU W ͕ྲྀߦΓΈΛਂΊ͍ͯͯɺϑϩ ϯτ૪͕աظΛܴ͍͑ͯͨ w ৽ن։ൃͷબࢶ͔Β#BDLCPOFͷྶѹ͕ফ͑ɺ
"OHVMBS͔3FBDU͔ͱ͍͏ײ͡ʹͳΓͦ͏ͳࠒ
443ΛܾΊͨϑϩʔ w ͱͱɺ3FOES BJSCOCͷ#BDLCPOFΛαʔόʔ Ͱ͑Δͭ ͬΆ͍࣮ͰKTʹ·ͭΘΔೋॏςϯ ϓϨʔτ࣮Λഁ໓͍ͤͨ͞ئ͕͋ͬͨ w #PPUIͰKTςϯϓϨʔτͷೋॏ࣮ʹർΕ͖͍ͬͯͨ
443ΛܾΊͨϑϩʔ w ϓϩτλΠϓதʹ'MVYJCMFͱ͍͏443ରԠͷ'8Λݟ ͚ͭͨͷͰɺ͍ܰϊϦͰ443Λࢼͨ͠ w ΅͘ʮOPEFͰ͍͍ͬͯʁʯ w 1.ʮ͍͍ͧʯ w ΅͘ʮ3FBDUͬͯͷͱ'MVYJCMFͬͯͷͰ443͕ʔʯ
w 1.ʮ͡ΌΜ͡ΌΜߦ͜͏ʯ
443ΛܾΊͨϑϩʔ w όοΫΤϯυͷෆ͔҆ΒSBJMTΤϯδχΞΛௐୡ w SBJMT͔ΒWJFXΛग़͢ͷઈରʹݏͩͬͨ ޙड़ w 1.ʮJ04൛ઈରಉ࣌ʹϦϦʔε͢Δͧʯ w
αʔϏεϦϦʔεॳ͔Β"1*͕ඞཁ w SBJMTαʔόʔ͔ΒWJFXΛग़ྗ͢Δͱɺ"1*ͱWJFX Ͱೋॏʹ࣮͕ඞཁʹͳͬͯ͠·͏
443ΛܾΊͨϑϩʔ w αʔϏεUVNCMSJOTUBHSBNͷΑ͏ͳʮλΠϜϥ Πϯʯ͕جຊϏϡʔɺϖʔδϯά࣮͕ඞਢ w SVCZͷJUFNUFNQMBUFʹKTͷJUFNUFNQMBUFΛ ॻ͍ͯ9)3ͰKTPOΛೖखͯ͠ΰϦΰϦϖʔδϯ άɺΈ͍ͨͳࠈಘͨ͘ͳ͍ w ͔ͯ͠͠8FCҰͭͷΫϥΠΞϯτͱݟͳͤΑ
͍ͷͰɺOPEFαʔόʔΛʮ8FC#SPXTFS͚ͷ ΞϓϦʯͬͯݴ͍ுΕͳ͍ͩΖ͏͔
443ΛܾΊͨϑϩʔ w ʮ8FCϒϥβ͚ͷΞϓϦʯͱ͍͏ঢ়ଶʹͳΔͱ ωΠςΟϒΞϓϦͱίϯςΩετ͕ڞ༗Ͱ͖Δ w "1*ͷར༻ํ๏ʹؔͯ͠ݟڞ༗͕Մೳɺ࣮ί ετΛݮΒͤΔ w SBJMTͷ࣮KTPO͚ͩΛΕΑ͘ͳΔɺUFNQMBUF ࣮͕ඞཁͳ͍ͷͰ࣮ίετΛݮΒͤΔ
443ΛܾΊͨϑϩʔ w .$ͱ7ͷؒʹΞʔΩςΫνϟͷน͕͋Δ͜ͱͰ ʮUFNQMBUFʹ͔͠ଘࡏ͠ͳ͍มʯ͕ੜଘͰ͖ͳ ͍ɺϝϯςφϯείετ͕ݮΒͤΔ w ΫϥΠΞϯτ͚࣮͕ޓ͍ʹґଘੑΛ࣋ͨͳ͍ w ͋ΔϓϥοτϑΥʔϜ͕ಛఆͷػೳΛαϙʔτ͢Δ ͔Ͳ͏͔ɺ७ਮʹ༏ઌͷʹू͞ΕΔ
443ΛܾΊͨϑϩʔ w KTͰੜ͢Δίϯςϯπ͕4&0తʹΞϨ͕ΞϨ͔ͩ ΒΞϨɺΈ͍ͨͳΛ͠ͳͯ͘Α͘ͳΔ ࣌ w OPEFKTαʔόʔΛSBJMTαʔόʔͱผʹཱͯͯ443 ͠Α͏ͥɺͱ͍͏ྲྀΕʹઆಘྗ͕༩͑ΒΕͨ
443ΛܾΊͨϑϩʔ w 443ཱ͕ͪͦ͏ͳγʔϯ w ΠςϨʔτ͢ΔϦονίϯςϯπΛఏڙ͍ͨ͠ w ςϯϓϨʔτͷೋॏ࣮Λආ͚͍ͨ w ϞόΠϧͱಉ࣌ϦϦʔε "1*͕࠷ॳ͔Βඞཁ
σϝϦοτ
σϝϦοτ w ॏ͍ɺ͍͍ͩͨͷͷ͕ॏ͍ɺͱʹ͔͘ॏ͍
σϝϦοτ w αʔόʔαΠυͰ"1*ϦΫΤετ)551 w Φʔόʔϔου͕େ͖͍ɺϨεϙϯεʹ͔͔Δ͕࣌ؒ Ұ൪ॏ͍ͱ͜ΖͰT͘Β͍͔͔ͬͯ͠·͏ w 3FOEFSFSҰͷಛݖΛ࣋ͨͳ͍ͨΊɺϢʔβʔ͕ϩά Πϯ͍ͯ͠Δ͔Ͳ͏͔Λ"1*ͷGFUDIແ͠ʹΓಘͳ͍ɺ ϧʔςΟϯάޙͷTUPSFͷঢ়ଶΛݟͯఆ͢Δ͔͠ͳ͍
w ͦͷͨΊʮ1SPNJTFBMMͰϦΫΤετΛશฒྻʹͯ͠ζ υϯʯͷΑ͏ʹ୯७ʹ͍͔ͳ͍ɺ4LFUDIͰ443࣌ ʹฒྻϦΫΤετΛճʹ͚ͯૹ͍ͬͯΔ
σϝϦοτ w ৴͢ΔKT͕ංେԽ͕ͪ͠ w XFCQBDLͰશͯΛUSBOTQJMF͢ΔͱKTίʔυʹDTT ؚ·ΕΔ͜ͱʹͳΔ w ݱ࣌ͰϑΝΠϧαΠζ.#ɺϞόΠϧΞϓ Ϧ͕ແ͍αʔϏεͰ͋Εݱ࣮తͳαΠζͰͳ͍ w
XFCQBDLͷMPBEFSઃఆʹґଘ͢ΔͷͰະѹॖՕॴΛ ࡧ͢Δͷ͕ࠔ ͜ͳ͍ͩDTTͷॏෳͱະѹॖͷͱ͜ ݟ͚ͭͯ.#͘Β͍ݮΒͨ͠
σϝϦοτ w ಄ͷ͓͔͍͠ίʔυ͕ॻ͚ͳ͍ w σʔλ"1*͔Β͔͠औͬͯ͜Εͳ͍͠ɺ͍ͬͺ ͍औΔͱͦΕ͚ͩϨεϙϯε͕͘ͳΔ w ͓·͚ʹKT͕མͪΔͱαʔόʔ͕ΤϥʔΛు͘ w खΑΓઃܭʹଟ͘ͷ࣌ؒΛׂ͘͜ͱʹͳΔ
w ʮԿ·Ͱʹ͜Ε࣮͠ͱ͍ͯʂϤϩγΫʂʯͬ ͯͳͬͨ࣌ʹͭΒ͍ɺ֬อ͠ͳ͚Ε͍͚ͳ͍࣌ ͕ؒগ͠ଟ͘ͳΔ
ϝϦοτ
ϝϦοτ w ಄ͷ͓͔͍͠ίʔυ͕ॻ͚ͳ͍ w KT͕ࣗσʔλΛೖखͯ͠දݱ͢ΔͷͰɺ༝དྷͷ ෆ໌ͳσʔλ͕ଘࡏ͠ͳ͍ʢςϯϓϨʔτʹྲྀ͠ ࠐ·Ε͍ͯΔมͳͲʣ w ࣮େม͚ͩͲɺશମ૾ΛѲͨ͠ਓ͕ॻ͘ͱ ͍͍ͩͨಉ͡Α͏ͳίʔυʹͳΔ
ϝϦοτ w ϓϥοτϑΥʔϜͷ֦ுੑ͕ߴ͍ w શͯͷϓϥοτϑΥʔϜ͕ʮ"1*ͱΫϥΠΞϯτ ΞϓϦʯͱ͍͏ಉҰͷϞσϧʹͳΔ w ͑֬͞อͰ͖ΕϦϦʔε͔࣌Βશͯͷϓϥο τϑΥʔϜ͚ʹΞϓϦ͕࡞Ͱ͖Δ
ϝϦοτ w ϓϥοτϑΥʔϜؒͷґଘੑ͕͍ w "1*ΛؚΉϓϥοτϑΥʔϜؒͷґଘੑ͕͍ͷͰɺ ҙͷλΠϛϯάͰΞϓϦػೳͷ։ൃΛ։࢝͠ɺ ҙͷλΠϛϯάͰఀࢭͰ͖Δ w 4LFUDIͰ"1*ʹSBJMTΛ࠾༻͍ͯ͠Δ͕ɺࣾͷݟɾ ϦϦʔε࣌ظɾઃܭϑϩʔͳͲͷ߹Ͱͨ·ͨ·࠾༻
͞Ε͍ͯΔ͚ͩ w ྫ͑ʮKTPO͔͠Βͳ͍͠(Pʹஔ͖͑Α͏ͥʯ ͱ͍͏Ͱ͖Δ
ϝϦοτ w ೋॏ࣮ͷօࡴ͠ w ϒϥβଆͰϖʔδϯάͨ͠ΓQVTI4UBUFΛαϙʔτ ͨ͠Γ͢Δࡍɺॳճग़ྗͱܧ͗͢༻ͷςϯϓϨʔτ Λೋॏʹߟྀ͢Δඞཁ͕ͳ͍ w ίʔυϕʔε͕ಉ͡+BWB4DSJQUͳͷͰͦͷ··͍ ճ͍͍ͤ
w ܧ͗͞ΕΔՕॴͷΈΞʔΩςΫνϟΛ·͍ͨͩڞ༗ ͷςϯϓϨʔτʹ͢Δͱ͔ɺ)5.-Λ"1*3FTQPOTFʹ ຒΊࠐΉͱ͔ɺͦ͏͍͏͜ͱΛ͠ͳ͍͍ͯ͘
w ϝϦοτͱσϝϦοτ͕͋ΔɺશͯͷΞϓϦέʔγϣ ϯͷύλʔϯʹద߹͢ΔສೳༀͰͳ͍ w ԼهͷΑ͏ͳϞνϕʔγϣϯʹରͯ͠༗༻ w ೋॏ࣮Λආ͚͍ͨ w αʔϏεΛϦονͳ41"ͱͯ͠ߏங͍ͨ͠ w
ෳͷϓϥοτϑΥʔϜΛಉ࣌ʹαϙʔτ͍ͨ͠ w ͱʹ͔͘ԿͰ͍͍͔Β443͕͍ͨ͠
ͦͷଞ
SFTQPOTF w )551ϦΫΤετ͕ϘτϧωοΫʹͳΔ w ͳΔ͘͘͢ΔͨΊ1SPNJTFBMMΛͬͯฒྻԽ w BTZODBXBJUͰ1SPNJTFBMMͨͭ͠ΛBXBJU͢Δ w ͜͜֎෦ґଘʹͳΔͨΊɺඞͣλΠϜΞτΛઃ ఆ͢Δ
SFTQPOTF srv.use(async (req, res, next) => { try { await
Promise.all([ request1, request2, request3, ]); next(); } catch (error) { next(error); } }); ͜͏͍͏ײ͡
6OIBOEMFE3FKFDUJPO w ඞͣVOIBOEMFE3FKFDUJPOΛࢹ͢Δ w ์ஔ͢ΔͱɺΤϥʔʹૺ۰ͨ͠ϢʔβʔͷϨεϙ ϯεΛλΠϜΞτͷݶք·Ͱػͯ͠͠·͏ w ͙ͯ͢͠σϓϩΠͰ͖ΔΑ͏ʹࢹ͓ͯ͘͠ w TFSWFS
QSPDFTTPO VOIBOEMFE3FKFDUJPO 'VOD w DMJFOU XJOEPXPOVOIBOEMFESFKFDUJPO'VOD
FYQSFTTFSSPSIBOEMF w FYQSFTTͰBSJUZ͕ͷGVODUJPOΛVTF͓ͯ͘͠ͱΤ ϥʔ࣌ͷGBMMCBDLʹͳΔ w ͍ͭ͜ͰIUNMͳͲΛฦ٫͢ΔΑ͏ʹ͓ͯ͘͠ w ࠷ۙ·ͰΕͯͯੜΤϥʔϖʔδ͕ग़͍ͯͨʢ໓ଟʹΤϯόά͠ͳ͔ͬͨͷ Ͱؾ͔ͳ͔ͬͨʣ
CBCFMMPBEFS w TFSWFSͱDMJFOUͰXFCQBDLͷCBCFMMPBEFSઃఆΛม ͑Δ w OPEFWҎ্Λ༻͍ͯ͠ΕɺBTZODBXBJUΛ αϙʔτ͍ͯ͠ΔͷͰCBCFMͷSFHFOFSBUPSͰ QPMZpMM͢Δඞཁ͕ͳ͍ w CBCFMQSFTFUFOWΛ͍TFSWFSଆΛOPEF
DVSSFOUͱ͢ΕΑ͍ɺQSPDFTTWFSTJPO͔Βద ͳQSFTFUΛબͯ͘͠ΕΔ
$PNQPOFOU࠶ར༻ w ͳΔ͘$PNQPOFOUΛ࠶ར༻͢Δ w ϨϯμϦϯάKTͷ৴αΠζίʔυΛॻ࣌͘ ؒόάͷಛఆɺ͘খ͘͞Ͱ͖Δ w DTTͷϚϯτɾΞϯϚϯτΧϯλʔॲཧ ͰऴΘΔͷͰΫϥΠΞϯτͷύϑΥʔϚϯε☝
$PNQPOFOU࠶ར༻ Button FollowButton ݟͨͷ੍ޚ Click ϑΥϩʔঢ়ଶͷ੍ޚ Button ݟͨͷ͜ͱ͚ͩ ঢ়ଶͷཧ͚ͩ
QBDLBHFKTPO w XFCQBDLͰQBDLBHFKTPOͰNBJOΩʔͷଞʹɺ CSPXTFSͱ͍͏Ωʔ͕ೝࣝͰ͖Δ w ϑΥϧμʹQBDLBHFKTPOΛஔ͍ͱ͍ͯɺͦͷ QBDLBHFKTPOʹCSPXTFSͱ͍͏ΩʔΛઃఆ͢Δ w ϒϥβଆͷϏϧυͰCSPXTFSͷϑΝΠϧΛ ͍ɺαʔόʔଆͷϏϧυͰNBJOΛ͏ɺͱ͍
͏͍͚͕Ͱ͖Δ w )551ͷϦΫΤελʔ͜ΕΛ͚͍ͬͯͯΔ
QBDLBHFKTPO
MPDBM4UPSBHF w MPDBM4UPSBHFΛར༻͢ΔͷΛΊɺ$PPLJFΛ4UPSBHF ͱͯ͠ར༻͢Δ w ͨͱ͑ϞόΠϧ͚ͷΞϓϦ༠ಋϔομʔͷද ࣔɾඇද੍ࣔޚ w 443࣌ʹϨϯμϦϯάͰ͖͍ͯͨํ͕SFQBJOU͕ ൃੜ͠ͳ͍ɺ$PPLJFʹ͍࣋ͬͯͨํ͕ॳظϩʔ
υύϑΥʔϚϯεͷ্ΛݟࠐΊΔ
ΤϯυϙΠϯτ w ͠Β͘ͷؒɺαʔόʔଆͷ෦ϦΫΤετͷΤϯ υϙΠϯτʹIUUQTTLFUDIQJYJWOFUͱ͍͏ϑ ϧͷ63-Λ͍ͬͯͨ w ໊લղܾͰ͍ͬͨΜ֎ʹग़ΔͱɺIUUQTͰड͚Δ DQVফඅΛճආ͢ΔͨΊɺαʔόʔϦΫΤετͰ ϑϩϯταʔόʔͷ*1Λ͏Α͏ઃఆͨ͠
w ςετKFTUͩͱ͔σϓϩΠTIJQJUͩͱ ͔ SFBDU@QFSGͩͱ͔αʔϏεॳظͰγʔυσʔ λͷूΊํ͕Ұ൪େࣄͩͱ͔&4-JOUͩͱ͔BTZOD BXBJUͩͱ͔%0.ͷྔΛ੍͢Δख๏ͩͱ͔).3 ͩͱ͔47(ΞΠίϯͩͱ͔ը૾ͷϋογϡϏϧυͩ ͱ͔Ϧϩʔυͳ͠ͰݴޠΓସ͑ΒΕΔͩͱ͔Ұ൪ ϝϞϦফඅͷগͳ͍TUPSFͷઃܭख๏ͩͱ͔σΟϨ ΫτϦอकํͱ͔Կ͔͍Ζ͍Ζ͋Γ͖͗ͯ͢͠
Εͳ͍ w ͕࣌ؒΓͳ͍ɺؾʹͳͬͨΒฉ͍͍ͯͩ͘͞
·ͱΊ w 443͍͍ͧ
Ҏ্