$30 off During Our Annual Pro Sale. View Details »
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
SPA実装最前線 ~今どきのJSフレームワーク選び~
Search
Yohei Isokawa
October 15, 2017
Programming
2
5k
SPA実装最前線 ~今どきのJSフレームワーク選び~
2017/10/14 上越TechMeetup #1 の資料です。
Yohei Isokawa
October 15, 2017
Tweet
Share
More Decks by Yohei Isokawa
See All by Yohei Isokawa
今どきのWebアニメーション実装
yuhiisk
0
870
writer.appを支える技術
yuhiisk
0
980
これからはじめるシングルページアプリケーション
yuhiisk
0
760
小学校段階からのプログラミング教育ってどうなる
yuhiisk
0
400
Critical CSS
yuhiisk
1
13k
Other Decks in Programming
See All in Programming
複数人でのCLI/Infrastructure as Codeの暮らしを良くする
shmokmt
5
2.3k
Socio-Technical Evolution: Growing an Architecture and Its Organization for Fast Flow
cer
PRO
0
330
Giselleで作るAI QAアシスタント 〜 Pull Requestレビューに継続的QAを
codenote
0
160
愛される翻訳の秘訣
kishikawakatsumi
2
320
手が足りない!兼業データエンジニアに必要だったアーキテクチャと立ち回り
zinkosuke
0
650
テストやOSS開発に役立つSetup PHP Action
matsuo_atsushi
0
150
AIエンジニアリングのご紹介 / Introduction to AI Engineering
rkaga
5
2.1k
DSPy Meetup Tokyo #1 - はじめてのDSPy
masahiro_nishimi
1
160
俺流レスポンシブコーディング 2025
tak_dcxi
14
8.6k
WebRTC、 綺麗に見るか滑らかに見るか
sublimer
1
160
AIコードレビューがチームの"文脈"を 読めるようになるまで
marutaku
0
350
Context is King? 〜Verifiability時代とコンテキスト設計 / Beyond "Context is King"
rkaga
9
1.1k
Featured
See All Featured
Why Our Code Smells
bkeepers
PRO
340
57k
KATA
mclloyd
PRO
32
15k
[RailsConf 2023 Opening Keynote] The Magic of Rails
eileencodes
31
9.8k
Product Roadmaps are Hard
iamctodd
PRO
55
12k
Building Adaptive Systems
keathley
44
2.9k
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
48
9.8k
Raft: Consensus for Rubyists
vanstee
141
7.2k
Testing 201, or: Great Expectations
jmmastey
46
7.8k
Thoughts on Productivity
jonyablonski
73
5k
How to train your dragon (web standard)
notwaldorf
97
6.4k
Design and Strategy: How to Deal with People Who Don’t "Get" Design
morganepeng
132
19k
Learning to Love Humans: Emotional Interface Design
aarron
274
41k
Transcript
41"࣮࠷લઢ 101$03/ ޒेɹ༸ฏ ʢ͍͔ͦΘɹΑ͏͍ʣ dࠓͲ͖ͷ+4ϑϨʔϜϫʔΫબͼd
ࣗݾհ w ޒे༸ฏʢΠιοϓʣ ্ӽࢢࡏॅͷϑϦʔϥϯεΤϯδχΞ ࢳڕࢢग़ w झຯɿυϩʔϯɺϤʔϤʔɺόεΓ w 5XJUUFSɿ!:VIJJTL w
IUUQCMPHZVIJJTLDPN
ΞδΣϯμ w γϯάϧϖʔδΞϓϦέʔγϣϯͷ͓͞Β͍ w ओཁϑϨʔϜϫʔΫ w 3FBDU w "OHVMBS w
7VFKT w ͦΕͧΕͷબͼͲ͜Ζ
γϯάϧϖʔδΞϓϦέʔγϣϯ ʢ4JOHMF1BHF"QQMJDBUJPOʣ
IUUQXXXBUNBSLJUDPKQBJUBSUJDMFTOFXTIUNM
w 8FCϖʔδΛ෦తʹߋ৽ w දࣔύϑΥʔϚϯεʹ༏Ε͍ͯΔ w Ϣʔβʔମݧʢ69ʣ্͕ɻ
'BDFCPPL
(PPHMF.BQ
ैདྷͷϖʔδભҠͷ8FCΞϓϦέʔγϣϯ ͱൺͯɺେ෯ʹ࣮ίετ͕͔͔Δɻ
࣮ίετΛԼ͛ΔͨΊɺ ͜͜ʙ̏ͰҰؾʹීٴͨ͠ͷ͕ɺ 41"࣮ʹಛԽͨ͠ +BWB4DSJQUϑϨʔϜϫʔΫɻ
ͦΕͧΕಛػೳ͕ଟ͍ͷͰɺͻͱͭͣͭ ࢼ͍ͯ͘͠ͷ͕࣌ؒඞཁɻ
ओཁ+BWB4DSJQUϑϨʔϜϫʔΫͷհ
None
w 'BDFCPPLࣾͷ6*ߏங༻ͷϥΠϒϥϦɻ w ࠓݱࡏੈքͰҰ൪ΘΕ͍ͯΔͱݴͬͯա ݴͰͳ͍΄Ͳਓؾɻ w ϑϨʔϜϫʔΫͰͳ͘ɺ͋͘·Ͱ7JFXΛ ୲͢ΔϥΠϒϥϦɻ
w ίϯϙʔωϯτࢦ
ίϯϙʔωϯτɹʹɹঢ়ଶɾػೳΛ࣋ͬͨ෦ ίϯϙʔωϯτΛΈ߹Θͤͯ ϖʔδΛߏங͢Δ
None
None
-> <Hello message="Hello world!" /> import React from 'react'; class
Hello extends React.Component { render() { return ( <div className="hello"> <h1>{this.props.message}</h1> </div> ); } }
w +49 w 9.-Λ֦ுͨ͠+BWB4DSJQUͷதʹ)5.-ίʔ υΛຒΊࠐΉͨΊͷΈ
render() { return ( <div className="button"> <button onClick={function() { alert('click');
}}> {this.props.text} </button> </div> ); }
w 7JSUVBM%0. w 3FBDUͷόοΫΤϯυʹ͋Δ%0.ߏΛந Խͨ͠σʔλߏ IUUQTDBMFOEBSQFSGQMBOFUDPNEJ⒎
w σʔλϞσϧͷߏมԽʹ߹Θͤͯ7JSUVBM %0.ͷલޙͷࠩΛࢉग़ w %0.ͷ࠶ඳըΛࠩͷ͋ͬͨՕॴ͚ͩߦ͏ IUUQTDBMFOEBSQFSGQMBOFUDPNEJ⒎
w σʔλϑϩʔΞʔΩςΫνϟͱͯ͠ʮ'MVYʯΛਪɻ w 'MVYʮσʔλͷྲྀΕΛҰํʹݶఆ͢Δઃܭύ λʔϯʯ
σʔλͷྲྀΕ͕ํʹͳΔ͜ͱͰɺγϯϓϧʹɻ
w 'MVYΛ࣮ݱ͢ΔͨΊʹɺ3FEVYͱ͍͏ঢ়ଶཧϥ ΠϒϥϦΛ༻͢Δͷ͕ϙϐϡϥʔɻ
w ࠷ۙ.PC9ਓؾɻ'MVYͱҟͳΔϦΞΫςΟϒ ͳσʔλϑϩʔΛఏڙɻ γϯϓϧͳ໘ɺઃܭྗ͕ඞཁɻ
w 3FBDUͷίʔυΛͦͷ··ΞϓϦʹ͢Δ 3FBDU/BUJWFɻ w ͱʹ͔͘ਓؾͳͷͰ8FC্Ͱͷใ͕ଟ͍ w ؔ࿈ϥΠϒϥϦ๛ 3FBDUͷϝϦοτ
w ඞཁͳͷΛࣗͰΈ߹ΘͤΔඞཁ͕͋Δ ʢϧʔςΟϯά"KBYɺσʔλཧͷϥΠϒ ϥϦͳͲʣ ˠSFBDUCPJMFSQMBUFɺDSFBUFSFBDUBQQ ɹ/FYUKT w σβΠφʔ͞Μͱڠۀ͢Δ߹ʹɺ+49͕ड ͚ೖΕΒΕͳ͍߹͕͋Δ 3FBDUͷσϝϦοτ
w ݱࡏͷόʔδϣϯͰ෦࣮͕ॻ͖͑ΒΕͨɻ ͜Ε͔ΒঃʑʹߴԽ͞Ε͍ͯ͘ɻ
Angular
w "OHVMBSϑϧελοΫͷ+BWB4DSJQUϑϨʔ ϜϫʔΫɻඞཁͳͷશͯೖͬͯΔɻ
w ίϯϙʔωϯτࢦ @Component({ selector: 'my-app', template: ` <h1>{{title}}</h1> ` })
export class AppComponent { title = 'Hello world!'; } <my-app></my-app>
w 7JSUVBM%0.
w 8FCඪ४Λҙ͍ࣝͯ͠Δɻ w &DNB4DSJQU w &4.PEVMFT w 8FCBOJNBUJPOT w
8FCDPNQPOFOUT w FUD
w "OHVMBSͰ5ZQF4DSJQUʢ"MU+4ʣΛ࠾༻ɻ ੩తܕ͚Λ༩ɻ
export class HeroesComponent implements OnInit { count: number; heroes: Hero[];
selectedHero: Hero; constructor(private heroService: HeroService) { } ngOnInit() { this.getHeroes(); } getHeroes(): void { this.heroService.getHeroes().then( heroes => this.heroes = heroes ); } }
+BWBͬΆ͍ɻ
w ಠࣗͷ)5.-ςϯϓϨʔτγεςϜ <h2>{{hero.name}} details!</h2> <div><img [src]="imagePath" /></div> <div><label (click)=“selectHero()">id: </label>{{hero.id}}</div>
<div> <label>name: </label> <input [(ngModel)]="hero.name" placeholder="name"> </div>
ςϯϓϨʔτߏจɺΩϞ͍
w %FQFOEFODZ*OKFDUJPO ґଘੑͷೖ
ڞ௨ॲཧΛఆٛͯ͠ɺ ίϯϙʔωϯτʹೖ͢Δ͜ͱͰ࠶ར༻Մೳʹ͢Δ IUUQCSBOEPODMBQQDPNXIBUJTEFQFOEFODZJOKFDUJPOBOEXIZJTJUVTFGVM
w BOHVMBSDMJʢίϚϯυϥΠϯπʔϧʣ $-*ͰίʔυΛੜͰ͖Δɻ ϕετϓϥΫςΟεɻ ng new PROJECT-NAME cd PROJECT-NAME ng
serve ng generate component my-new-component
w όʔδϣϯʹΑͬͯݺͼํ͕ҧ͏ɻ WY"OHVMBS+4 WYd"OHVMBS WYd"OHVMBS ˞8FC্ͰใΛ୳͢ͱ͖ҙɻ
w ඞཁͳػೳશͯ༻ҙ͞Ε͍ͯΔ ༨ܭͳ͜ͱΛߟ͑ͳ͍͍ͯ͘ɻ w 8FCඪ४ΛҙࣝͰ͖ΔͷͰɺ࠷৽ٕज़Λ࠾༻Ͱ͖Δɻ ޙʑͷҠߦ͕؆୯ w ϓϩδΣΫτ͝ͱͷϧʔϧԽ͕༰қɻ w ͘։ൃΛճͤΔ
"OHVMBSͷϝϦοτ
w ֶशίετ͕͔͔Δ ɾ"OHVMBSͷ"1* ɾ5ZQF4DSJQU ɾ3Y+4 ɾ4ZTUFNKT ɾ;POFKT "OHVMBSͷσϝϦοτ
w ࠓ݄தʹWʹϝδϟʔΞοϓσʔτɻ w ͱ͖ͬͭͮΒ͍͚ͲɺݸਓతʹҰ൪ָ͍͠ϑϨʔ ϜϫʔΫɻ
Vue.js
w 7VFKT.77.ͱ͍͏.7$ͷੜछΛઃܭج൫ͱ ͯ͠ߏங͞Εͨɺ+BWB4DSJQUϑϨʔϜϫʔΫɻ w 7VF Ϗϡʔ ͱൃԻɻ w தࠃͰਓؾɻຊࠃͰѻ͍͍͢ͱਓؾ͕ߴ ·͍ͬͯΔɻ
w ίϯϙʔωϯτࢦ <template> <div class="hello"> <h1>{{ msg }}</h1> </div> </template>
<script> export default { name: 'hello', data () { return { msg: 'Welcome to Your Vue.js App' } } } </script> <hello></hello>
w 7JSUVBM%0.
w 7JFXͷϥΠϒϥϦ ςϯϓϨʔτΤϯδϯͷΈ߹ Θͤɺ3FBDUͱ"OHVMBSͷதؒɻ ͍͍ͱ͜औΓɻ <span v-bind:title="message">hello</span> <ul id="example-1"> <li
v-for="item in items"> {{ item.message }} </li> </ul>
w TDSJQUλάͰಡΈࠐΊΔ <script src="https://unpkg.com/vue"></script>
w TDSJQUλάͰಡΈࠐΊΔ <div id="app"> <p>{{ message }}</p> </div> <script> var
app = new Vue({ el: '#app', data: { message: 'Hello Vue.js!' } }); </script>
w ୯ҰϑΝΠϧίϯϙʔωϯτ <template> <div id=“app”>…</div> </template> <script> export default {
name: 'app' } </script> <style> #app { font-family: 'Avenir', Helvetica, Arial, sans-serif; } </style>
w WVFDMJʢίϚϯυϥΠϯπʔϧʣͰ ͻͳܗੜɻ $ vue init webpack my-project $ cd
my-project $ npm install $ npm run dev
w 3FEVYϥΠΫͳʮ7VFYʯͱ͍͏ঢ়ଶཧϥΠϒϥ ϦΛ͏ͷ͕Ұൠత
w 8FFYͰωΠςΟϒΞϓϦ։ൃ ·࣮ͩ༻తͰͳ͍ײ͡
w 443/VYUKT ʢϢχόʔαϧΞϓϦέʔγϣϯ༻ϑϨʔϜϫʔΫʣ
w γϯϓϧͰ͋Δ w খ͍͞ΞϓϦέʔγϣϯͷ։ൃʹҰ൪ద͍ͯ͠Δ TDSJQUλάͰಡΈࠐΊ࠷ݶ͑Δ w ެࣜͷຊޠυΩϡϝϯτ͕ͱͯΘ͔Γ͍͢ 41"࣮ॳ৺ऀ͖ɻ 7VFKTͷϝϦοτ
w ࡢͷϦϦʔε͔Β͕࣌ؒܦͬͯͳ͍ͷͰɺଞͷϑ ϨʔϜϫʔΫΑΓϦιʔε͕·ͩະख़ɻ ϥΠϒϥϦɾΤσΟλͷαϙʔτ͕ෆ 7VFKTͷσϝϦοτ
w γϯϓϧͰѻ͍͍͢ͷͰɺ͜Ε͔Β3FBDUΑΓ 7VF͕ਓؾɾधཁ͕ߴ·Δ༧ɻ
݁ہͲΕ͕͍͍ʁ
w ࣮ίετΛ͍͑ͨ࣌ʹɻ w %0.Λॻ͖͑Δ͜ͱ͕ଟ͍ΞϓϦέʔγϣϯʹ w ಉ͡ػೳͷωΠςΟϒΞϓϦΛ࡞͢Δ߹ɻ ʢ3FBDU/BUJWFͰΞϓϦ։ൃʣ 3FBDUͷબͼͲ͜Ζ
w ػೳΛͻͱ௨Γ֮͑ͯ͠·͑ɺ͘ݎ࿚ͳΞϓϦ έʔγϣϯߏங͕Ͱ͖Δɻ w େن։ൃʹڧ͍ɻ w ཧը໘ͳͲͷσʔλද͕ࣔଟ͍Α͏ͳΞϓϦέʔ γϣϯͱ૬ੑ͕ྑ͍ɻ w ֶशίετ͕ߴ͍ͷͰɺϓϩδΣΫτϝϯόʔͷε
Ωϧʹґଘɻ "OHVMBSͷબͼͲ͜Ζ
w ϓϩδΣΫτϝϯόʔͷ41"࣮ܦݧ͕গͳ ͍߹ʹɻ w খʙେنͷൣғͷ։ൃͰ͑Δɻ w 8FCαΠτͷ੍࡞ͰޮՌΛൃشɻ K2VFSZͷΘΓ 7VFKTͷબͼͲ͜Ζ
w ͓͢͢Ίͷൺֱํ๏ɺ؆୯ͳΞϓϦέʔγϣϯΛ ֤ϑϨʔϜϫʔΫͰ࡞ͬͯΈΔɻ w 50%0ΞϓϦɺΘ͔Γ͍͢ಈ࡞ͷͷɺ ෳը໘ͷϧʔςΟϯάઃఆ w ετʔϦʔϒοΫ ʢIUUQTTUPSZCPPLKTPSHʣͰࢼͯ͠ΈΔɻ 6*ίϯϙʔωϯτͷ։ൃڥɻ
ϕετϓϥΫςΟε
ϓϩδΣΫτͷେ͖͞ʁ ͲΕ΄ͲͷظؒͰϝϯςφϯεͰ͖Δ͔ʁ ͯ͢ͷػೳΛ͡ΊʹఆٛͰ͖Δ͔ɺͦΕͱॊೈੑΛ࣋ͨͤΔ Α͏ཁٻ͞Ε͍ͯΔ͔ ͯ͢ͷػೳ͕ఆٛ͞Ε͍ͯΔͳΒɺͲΜͳػೳɾೳྗ͕ඞཁ͔ʁ
υϝΠϯϞσϧϏδωεϩδοΫෳࡶ͔ʁ 8FC͔ϞόΠϧ͔σεΫτοϓ͔ɺͲͷΑ͏ͳϓϥοτϑΥʔϜ͕ λʔήοτ͔ʁ αʔόʔαΠυϨϯμϦϯά͕ඞཁ͔ʁ4&0ॏཁ͔ʁ ϦΞϧλΠϜΠϕϯτΛଟ͘ѻ͏͔ʁ ϓϩδΣΫτνʔϜͷਓʁ νʔϜͷ։ൃऀͨͪͷܦݧʁͲͷΑ͏ͳܦྺͳͷ͔ʁ ͦͷ··͙͢ʹ͑ΔίϯϙʔωϯτϥΠϒϥϦʔͳ͍͔ʁ அج४Λ͓ͬͯ͘
·ͱΊ
w ओཁϑϨʔϜϫʔΫͭ ɾ3FBDU ɹॊೈɺϦιʔε͕๛ɺωΠςΟϒΞϓϦԽ ɾ"OHVMBS ɹ༨ܭͳ͜ͱΛߟ͑ͳ͍͍ͯ͘ɺେن։ൃʹڧ͍ ɾ7VFKT ɹγϯϓϧͰѻ͍͍͢ɺͲͷنͰରԠͰ͖Δ ·ͱΊ
w ͦΕͧΕҰҰɻͲΕ͕ྑ͍ͱҰ֓ʹݴ͑ͳ͍ w அج४Λ౿·͑ͨબΛ ·ͱΊ