Slide 1

Slide 1 text

ഁ୼͠ͳ͍ Vue.js ΞϓϦέʔγϣϯ։ൃͷͨΊʹ େ੾ͳ͜ͱ 2018.09.15 HANATANI Takuma

Slide 2

Slide 2 text

Profile • Ֆ୩ ୓ຏ as known as potato4d • Vue.js / Nuxt.js Japanese Document • Translator / maintainer • Vue.js Japan user group • Staff / Vue Fes Japan 2018 staff • Nuxt.js beginners guide author

Slide 3

Slide 3 text

What's JSLounge produced by ElevenBack ? ΦϑϥΠϯΠϕϯτ ΦϯϥΠϯڭࡐఏڙ اۀ޲͚ߨश https://jslounge.connpass.com https://jslounge-archives.elevenback.jp/ https://blog.elevenback.jp

Slide 4

Slide 4 text

ࠓ೔ͷΰʔϧ

Slide 5

Slide 5 text

ࠓ೔ͷΰʔϧ • طଘίʔυͷෛ࠴ • ͍ͭ࡞Γม͑Δ͔ͷ೰Έ • Vue.js ͷΞϯνύλʔϯ΁ͷ՝୊ײ

Slide 6

Slide 6 text

ࠓ೔ͷΰʔϧ • طଘίʔυͷෛ࠴ • ͍ͭ࡞Γม͑Δ͔ͷ೰Έ • Vue.js ͷΞϯνύλʔϯ΁ͷ՝୊ײ • ίʔυͷʮࣺͯͲ͜Ζʯ΁ͷཧղ • ϑϩϯτΤϯυͷ଱༻೥਺ͷ೺Ѳ • ഁغ͍ͯ͘͜͠ͱΛલఏͱͨ͠ઃܭ

Slide 7

Slide 7 text

ࠓ೔࿩͢͜ͱ • ݱࡏͷϑϩϯτΤϯυΞϓϦέʔγϣϯͷ଱༻೥਺ʹ͍ͭͯ • Vue.js Ͱඞཁ೥਺૸Γ੾ΔͨΊʹඞཁͳجຊతͳߟ͑ํ • ࣮ྫ͔ΒֶͿϝϯςφϏϦςΟΛԼ͛Δίʔυͱઃܭ • Vue CLI / Nuxt.js ʹΑΔഁ୼ͮ͠Β͍։ൃ؀ڥͷߏங…

Slide 8

Slide 8 text

ࠓ೔࿩͢͜ͱ • ݱࡏͷϑϩϯτΤϯυΞϓϦέʔγϣϯͷ଱༻೥਺ʹ͍ͭͯ • Vue.js Ͱඞཁ೥਺૸Γ੾ΔͨΊʹඞཁͳجຊతͳߟ͑ํ • ࣮ྫ͔ΒֶͿϝϯςφϏϦςΟΛԼ͛Δίʔυͱઃܭ • Vue CLI / Nuxt.js ʹΑΔഁ୼ͮ͠Β͍։ൃ؀ڥͷߏங

Slide 9

Slide 9 text

଱༻೥਺ʹ͍ͭͯ • ࣮ࡍͷ։ൃͷγʔϯͰ͸໰୊ͳ͘ϝϯςφϯεͰ͖Δͷ͸2,3 ೥͕ݶ౓ • ΞʔΩςΫνϟ΍ϓϩάϥϜͷࢹ఺͚ͩࡁΉ໰୊Ͱ͸ͳ͍ • ྫ͑͹υϝΠϯ֓೦ͷݟ௚͠΁ͷ௥ै • ྫ͑͹σβΠϯϦχϡʔΞϧ΁ͷ௥ै • ٕज़τϨϯυʹ߹Θͤͨભٶ

Slide 10

Slide 10 text

υϝΠϯ֓೦ͷݟ௚͠ • ʮ͜ͷػೳ͸౰ॳ͸͚͋ͬͨΕͲผػೳʹ౷߹͠Α͏ʯ • ʮҙຯ͢Δͱ͜Ζ͕มΘͬͨͷͰશମΛϦωʔϜ͠Α͏ʯ • ʮ࡟আ͠Α͏ʯ

Slide 11

Slide 11 text

σβΠϯϦχϡʔΞϧ΁ͷ௥ै • ʮϦϒϥϯσΟϯάͷͨΊʹશମΛϦχϡʔΞϧ͍ͨ͠ʯ • ʮ(ϚςϦΞϧͷΑ͏ͳ)ۀքͷτϨϯυ͕ҠͬͨͷͰ߹Θ͍ͤͨʯ • ʮUIϑϨʔϜϫʔΫϕʔε͚ͩͬͨͲಠࣗʹ͍ͨ͠ʯ

Slide 12

Slide 12 text

ٕज़τϨϯυʹ߹Θͤͨมભ • Vue.js 1.0 ͸ 3 ೥લɺ Vue.js 2.0 ͸ 2 ೥લɺ࣍ͷ v3 ͸…… • ʮݹ͘ͳΔͱ৘ใ΋૿͑ͣศརͳ΋ͷ΋࢖͑ͳ͍ʯ • ʮՄೳͰ͋Ε͹࣌ؒΛͱͬͯ΋࠷௿ݶϝδϟʔ͸͍͋͛ͨʯ

Slide 13

Slide 13 text

ٕज़τϨϯυʹ߹Θͤͨมભ • খ͞ͳτϨϯυ୯ҐͰ΋τϨϯυ͸มΘΔ • ࣌ࠁૢ࡞͸ day.js ͕ moment ͷ୅ΘΓʹͳ͍ͬͯΔ͔΋ • HTTP ௨৴΋ XHR ͳ axios Ͱ͸ͳ͘ fetch ϕʔεͷ΋ͷ͔΋

Slide 14

Slide 14 text

࠷ऴతʹ࢒Δͷ͸……ʁ ✘ Vue.js ΍ UI ʹܹ͘͠ґଘͨ͠෦෼ ✘ Build environment ✘ ྲྀߦΓͷϥΠϒϥϦʹΑ࣮ͬͯ૷͞Εͨ෦෼ ✘ υϝΠϯશҬ(ഽײίʔυϕʔεͷ6ׂఔ౓͸Ҡ২Մೳ) ˕ ϓϩδΣΫτʹ͋Θ͍ͤͨΘΏΔʮϢʔςΟϦςΟʯ ˕ ൚༻తͳ(Ξφ΢ϯε΍௨஌ͳͲͷ)ίϯϙʔωϯτͷϩδοΫ

Slide 15

Slide 15 text

࠷ऴతʹ࢒Δͷ͸……ʁ ΋͍͚ͬͯΔͷ͸஌ࣝͱܦݧ มΘΔ͜ͱΛલఏʹʮࣺͯ΍͍͢ʯίʔυΛ࡞Δ = ϑϩϯτΤϯυ͸ϩʔάϥΠΫ

Slide 16

Slide 16 text

ࠓ೔࿩͢͜ͱ • ݱࡏͷϑϩϯτΤϯυΞϓϦέʔγϣϯͷ଱༻೥਺ʹ͍ͭͯ • Vue.js Ͱඞཁ೥਺૸Γ੾ΔͨΊʹඞཁͳجຊతͳߟ͑ํ • ࣮ྫ͔ΒֶͿϝϯςφϏϦςΟΛԼ͛Δίʔυͱઃܭ • Vue CLI / Nuxt.js ʹΑΔഁ୼ͮ͠Β͍։ൃ؀ڥͷߏங…

Slide 17

Slide 17 text

جຊతͳߟ͑ํ ʮࣺͯ΍͍͢ʯίʔυͷͨΊʹ…… 1. ʮ࠶ར༻ੑʯ΁ͷແؔ৺ͱݻࣥ͸ಟ 2. Vuex͸ԿͷͨΊʹ͋Δ͔Λߟ͑Δ 3. Vue.js ͓Αͼ SFC ʹͩ͜ΘΓ͗͢ͳ͍ ͜͜Ͱ͸֓೦ͷΈɺ࣮ྫ͸࣍ͷηΫγϣϯͰɹ⾣

Slide 18

Slide 18 text

ʮ࠶ར༻ੑʯ΁ͷແؔ৺ͱݻࣥ͸ಟ • ੹຿ͷଟ͍ίʔυ͸·ͱΊͯഁغ͢Δඞཁ͕ग़ͯ͘Δ • ͔ͱݴͬͯ Vuex ͳͲͷάϩʔόϧͳσʔλʹ҆қʹґଘ͢Δ ͱࠜຊతͳվमʹ଱͑ΒΕͳ͍ • ϓϨθϯςʔγϣϯ૚ͷͨΊ͚ͩͷσʔλ͸൚༻ੑΛٻΊΔ • ϩδοΫ͸୯ମͰ͸ՄೳͳݶΓബ͘ॻ͘ • ͳͲͳͲ……

Slide 19

Slide 19 text

Vuex ͸ͳΜͷͨΊʹ͋Δ͔Λߟ͑Δ • શͯͷσʔλΛೖΕͯ͠·͏ͱͦΕ͸ͨͩͷάϩʔόϧม਺ • ϩʔΧϧεςʔτͱ͏·͘࢖͍෼͚Δ • Vuex Λͨͩͷശͱͯ͠ஔ͘ͷ͔ɺϦΞΫςΟϒͳυϝΠϯϨ ΠϠʔΛߏங͢Δج൫ͱ͢Δͷ͔Λ͸͖ͬΓͤ͞Δ • ͳͲͳͲ……

Slide 20

Slide 20 text

Vue.js / SFC ʹͩ͜ΘΓ͗͢ͳ͍ • Vue.js ͔ͩΒͱ͍ͬͯશͯΛ .vue Ͱ׬݁ͤ͞Δඞཁ͸ͳ͍ • SFC ͸ Vue Test Utils Λར༻ͨ͠είʔϓͷେ͖͍ςετͳͲ ͕ඞཁʹͳΔͷͰඞવੑͷ͋Δ੹຿͚ͩΛ΋ͨͤΔ • ͋ͱ͸ VanillaJS ʹΑΔهड़Λ৺͕͚Δ • ৄ͘͠͸࣍ͷηΫγϣϯͰ

Slide 21

Slide 21 text

ࠓ೔࿩͢͜ͱ • ݱࡏͷϑϩϯτΤϯυΞϓϦέʔγϣϯͷ଱༻೥਺ʹ͍ͭͯ • Vue.js Ͱඞཁ೥਺૸Γ੾ΔͨΊʹඞཁͳجຊతͳߟ͑ํ • ࣮ྫ͔ΒֶͿϝϯςφϏϦςΟΛԼ͛Δίʔυͱઃܭ • Vue CLI / Nuxt.js ʹΑΔഁ୼ͮ͠Β͍։ൃ؀ڥͷߏங

Slide 22

Slide 22 text

࠶ར༻ੑͷײ֮஋ͷζϨ

Slide 23

Slide 23 text

͜Μͳίϯϙʔωϯτ࡞ͬͯ·ͤΜ͔ʁ Like import { mapActions } from ‘vuex’ export default { props: { id: Number }, methods: { click() { this.like({ id }) }, .. .mapActions(‘entries’, [‘like’])
 }
 } -JLF#VUUPOWVF

Slide 24

Slide 24 text

͜Μͳίϯϙʔωϯτ࡞ͬͯ·ͤΜ͔ʁ Like import { mapActions } from ‘vuex’ export default { props: { id: Number }, methods: { click() { this.like({ id }) }, .. .mapActions(‘entries’, [‘like’])
 }
 } Atoms ૬౰ͷϞϊ͕ Vuex ʹґଘ͍ͯ͠Δ -JLF#VUUPOWVF

Slide 25

Slide 25 text

վળྫ Like export default { methods: { click(event) { this.$emit('click', event) } }
 } Vue.js ͷΠϕϯτγεςϜΛ࢖ͬͯ੹຿Λബ͘ -JLF#VUUPOWVF

Slide 26

Slide 26 text

͜Μͳίϯϙʔωϯτ࡞ͬͯ·ͤΜ͔ʁ
export default { props: { mode: String } } 6TFS'PSNWVF

Slide 27

Slide 27 text

͜Μͳίϯϙʔωϯτ࡞ͬͯ·ͤΜ͔ʁ
export default { props: { mode: String } } ίϯϙʔωϯτʹೋͭҎ্ͷ໾ׂ͕͋Δ 6TFS'PSNWVF

Slide 28

Slide 28 text

վળྫ
export default { } 6TFS$SFBUF'PSNWVF ৑௕ʹͳͬͯ΋ͦΕͧΕผͷίʔυʹ͢Δ

Slide 29

Slide 29 text

վળྫ
export default { } 6TFS&EJU'PSNWVF ผͷίʔυʹ͓ͯ͘͠ͱʮߋ৽ෆՄʯͷ߲໨ͷ࣮૷΋༰қ

Slide 30

Slide 30 text

VuexʹدͤΔ΂͖ίʔυͱ دͤΔ΂͖Ͱ͸ͳ͍ίʔυ

Slide 31

Slide 31 text

͜ΜͳίʔυΛॻ͍ͯ·ͤΜ͔ʁ import { mapGetters, mapActions } from 'vuex' export default { computed: { ...mapGetters('entries', { form: 'editEntry' })
 }, methods: { ...mapActions('entries', ['updateEditEntry', 'updateEntry']) } } &OUSZ&EJU'PSNWVF

Slide 32

Slide 32 text

͜ΜͳίʔυΛॻ͍ͯ·ͤΜ͔ʁ import { mapGetters, mapActions } from 'vuex' export default { computed: { ...mapGetters('entries', { form: 'editEntry' })
 }, methods: { ...mapActions('entries', ['updateEditEntry', 'updateEntry']) } } &OUSZ&EJU'PSNWVF 1. ίϯϙʔωϯτ͚͕ͩ஌͍ͬͯΕ͹ྑ͍தؒঢ়ଶʹVuexΛ࢖͍ͬͯΔ 2. Vuex ͷ mapXXX ͷΤΠϦΞεػೳͷ͍ͤͰ grep ͮ͠Β͘ͳ͍ͬͯΔ

Slide 33

Slide 33 text

͜ΜͳίʔυΛॻ͍ͯ·ͤΜ͔ʁ /* ... state code ... */ const getters = { entries: [], editEntry: null } /* ... mutation code ... */ const actions = { // ... other actions updateEditEntry({ commit }, { formData }) {commit('updateEditEntry', formData)} } export default { namespaced: true, state, mutations, getters, actions } FOUSJFTKT υϝΠϯ֓೦͕ೖ͍ͬͯΔ͸ͣͷ entries ʹԿނ͔ϑΥʔϜͷঢ়ଶ͕

Slide 34

Slide 34 text

मਖ਼ྫ import { mapGetters, mapActions } from 'vuex' export default { data() { const form = this.entries.find((e) => e.id == this.$route.params.id)) return { form
 } }, computed: { ...mapGetters('entries', ['entries'])
 }, methods: { ...mapActions('entries', ['updateEntry']) } } &OUSZ&EJU'PSNWVF 1. தؒঢ়ଶ͸ϩʔΧϧεςʔτʹด͡ࠐΊͯ Vuex ʹΰϛσʔλ͕࢒Βͳ͍Α͏ʹ 2. ೖྗ͕Ωϟϯηϧ͞Εͨ৔߹΋ίϯϙʔωϯτͷϥΠϑαΠΫϧʹΑͬͯద੾ʹഁغ

Slide 35

Slide 35 text

मਖ਼ྫ /* ... state code ... */ const getters = { entries: [] } /* ... mutation code ... */ const actions = { updateEntry() {} // ࣮ࡍͷσʔλͷߋ৽͚ͩΛߦ͏ } export default { namespaced: true, state, mutations, getters, actions } FOUSJFTKT Vuex ͸࣮σʔλʹͷΈઐ೦Ͱ͖ɺ͔ͭԼखʹϦηοτॲཧΛॻ͔ͳ͍Ͱྑ͍Α͏ʹ

Slide 36

Slide 36 text

Single File Component vs VanillaJS

Slide 37

Slide 37 text

͜ΜͳίʔυΛॻ͍ͯ·ͤΜ͔ʁ export default { data() { return { formData: { val1: '', val2: '' }, status: '' } // ద౰ͳঢ়ଶ
 } methods: { handleAction() {
 const foo = this.covert({…this.formData}) this.$store.dispatch('namespace/someAction', foo)
 }, convert(args) { return {...args} // Կ͔͠ΒͷॲཧΛߦͬͨޙʹฦ٫ } } } .Z$PNQPOFOUWVF

Slide 38

Slide 38 text

͜ΜͳίʔυΛॻ͍ͯ·ͤΜ͔ʁ export default { data() { return { formData: { val1: '', val2: '' }, status: '' } // ద౰ͳঢ়ଶ
 } methods: { handleAction() {
 const foo = this.covert({…this.formData}) this.$store.dispatch('namespace/someAction', foo)
 }, convert(args) { return {...args} // Կ͔͠ΒͷॲཧΛߦͬͨޙʹฦ٫ } } } ୯ҰϑΝΠϧίϯϙʔωϯτͰ΋ͭඞཁͷͳ͍ॲཧ͕ଘࡏ͢Δ (ಛʹෳ਺ͷίϯϙʔωϯτͰग़ݱ͢Δ৔߹) .Z$PNQPOFOUWVF

Slide 39

Slide 39 text

मਖ਼ྫ function convert(args) { return {...args}
 } export default convert VUJMTDPOWFSUFSKT JavaScript ͚ͩͰ׬݁͢Δ෦෼͸ JavaScriptͰ੾Γग़͢

Slide 40

Slide 40 text

मਖ਼ྫ import convert from './converter' describe('converter.js', () => { test('test code', () => { const input = { val1: '', val2: '' } expect(convert(input)).toMatchObject(input) }) }) TQFDVUJMTDPOWFSUFSTQFDKT JavaScript Ͱॻ͘͜ͱͰςετίʔυ΋هड़͠΍͘͢

Slide 41

Slide 41 text

ࠓ೔࿩͢͜ͱ • ݱࡏͷϑϩϯτΤϯυΞϓϦέʔγϣϯͷ଱༻೥਺ʹ͍ͭͯ • Vue.js Ͱඞཁ೥਺૸Γ੾ΔͨΊʹඞཁͳجຊతͳߟ͑ํ • ࣮ྫ͔ΒֶͿϝϯςφϏϦςΟΛԼ͛Δίʔυͱઃܭ • Vue CLI / Nuxt.js ʹΑΔഁ୼ͮ͠Β͍։ൃ؀ڥͷߏங…

Slide 42

Slide 42 text

Vue CLI v3 • Vue.js ۘ੡ͷ CLI πʔϧ • طଘͷ؀ڥ(ࣗྗͰ webpack Λ৮Δ؀ڥ)͔Β΋Ҡߦ͠΍͍͢ • CLIπʔϧͷԆ௕Β͍͠ػೳ͕๛෋ • ϓϥάΠϯʹΑΔ؀ڥͷڧԽ͕༰қ • ϓϥάΠϯʹΑΔ؀ڥͷߏங͕༰қ • ίϚϯυҰൃͰςετ؀ڥͳͲΛ࡞੒Մೳ • ։ൃମݧͱͯ͠͸؀ڥ΍଍ճΓΛڧԽ͢Δཁૉ͕ڧ͍

Slide 43

Slide 43 text

7VFKT1SPKFDU 5FTUJOH Nuxt.jsΛ༗ޮ׆༻͢Δ 7VFKT 7VF3PVUFS 7VFY 7VF5FTU6UJMT 1VSF+BWB4DSJQU &YUFSOBM4FSWJDF )551 6UJMJUZ CVJMEFOWJSPONFOU CVJMEFOWJSPONFOU CVJMEFOWJSPONFOU

Slide 44

Slide 44 text

7VF$-*W1SPKFDU 7VF$-*4FSWJDF 5FTUJOH Vue CLI v3 ༗ޮ׆༻͢Δ 7VFKT 7VF3PVUFS 7VFY 7VF5FTU6UJMT 1VSF+BWB4DSJQU &YUFSOBM4FSWJDF )551 6UJMJUZ

Slide 45

Slide 45 text

Nuxt.js • Vue.js ͔ΒݟΔ৔߹͸ඇެࣜͷϑϨʔϜϫʔΫ • Vue.js ͷίϛϡχςΟύʔτφʔͱͳͬͨͷͰڠྗؔ܎Ͱ͸͋Δ • ϑϨʔϜϫʔΫΒ͍͠ػೳΛఏڙ͢Δ • ಠࣗͷϞδϡʔϧ΍ϓϥάΠϯγεςϜ • ΦʔτϩʔσΟϯάܥͷػೳ΍ SSR ͷσϑΥϧταϙʔτ • ϓϩδΣΫτͷجຊઃܭΛ Nuxt.js ʹ೚ͤΔ͜ͱ͕Ͱ͖Δ • ։ൃମݧͱͯ͠͸ϓϩδΣΫτઃܭΛڧԽ͢Δཁૉ͕ڧ͍

Slide 46

Slide 46 text

7VFKT1SPKFDU 5FTUJOH Nuxt.jsΛ༗ޮ׆༻͢Δ 7VFKT 7VF3PVUFS 7VFY 7VF5FTU6UJMT 1VSF+BWB4DSJQU &YUFSOBM4FSWJDF )551 6UJMJUZ CVJMEFOWJSPONFOU CVJMEFOWJSPONFOU CVJMEFOWJSPONFOU

Slide 47

Slide 47 text

/VYUKT1SPKFDU 5FTUJOH /VYUKT Nuxt.jsΛ༗ޮ׆༻͢Δ 7VFKT 7VF3PVUFS 7VFY 7VF5FTU6UJMT 1VSF+BWB4DSJQU &YUFSOBM4FSWJDF )551 6UJMJUZ webpack vue-meta vue-server-renderer Project structure

Slide 48

Slide 48 text

Vue CLI v3 or Nuxt.js • ར༻Ϟνϕʔγϣϯ͔Βͯ͠ҧ͏ͷͰҰ֓ʹ͸ൺֱతͰ͖ͳ͍ • ݸਓతʹ͸ Vue.js ͷϏΪφʔ͕গͳ͍৔߹͸ Nuxt.js Λਪ঑ • ͍͖ͳΓ Nuxt.js Λ৮Δͷ͸ϋʔυϧ͕ߴ͍ͷͰඇਪ঑ • ͋Δఔ౓׳Εͨਓ͕ Nuxt.js ͰҰ௨Γ૊ΜͰ͠·͑͹ϏΪφʔ͕͋ ͱ͔Βೖͬͯ΋յΕͳ͍Α͏ͳઃܭ͕Ͱ͖Δ • ͲͷΈͪ 2 ೥ఔ౓ͷεύϯͰߟ͑ΔͳΒϨʔϧʹ৐ͬͯߴ͍ੜ࢈ ੑΛಘͨ΄͏͕ϓϩδΣΫτΛυϥΠϒͰ͖Δ

Slide 49

Slide 49 text

thanks!