Aplicaciones de una sola página con Vue.js y Flask: configuración de Vue.js

Introducción Esta es la publicación de apertura de una serie de tutoriales sobre el uso de Vue.js y Flask para el desarrollo web de pila completa. En esta serie voy a demostrar h...

Configuración y familiarización con Vue.js

Introducción

Esta es la publicación inicial de una serie de tutoriales sobre el uso de Vue.js y Matraz para el desarrollo web completo. En esta serie, demostraré cómo crear una aplicación web de encuestas en la que la arquitectura de la aplicación consiste en un front-end compuesto por una aplicación de página única (SPA) Vue.js y una API REST de back-end utilizando el marco web Flask.

Esta primera publicación cubrirá la configuración y estructura básica del proyecto, utilizando la directiva v-for de Vue.js y las etapas del ciclo de vida del componente.

Contenido de la serie

  1. Configuración y familiarización con Vue.js (usted está aquí)
  2. Navegación por el enrutador Vue
  3. Gestión de estados con Vuex
  4. API RESTful con Flask
  5. Integración AJAX con API REST
  6. Autenticación JWT
  7. Implementación en un servidor privado virtual

Configuración de frontend con vue-cli y webpack

Usaré dos herramientas muy importantes para un proyecto de Vue.js, que son las Interfaz de línea de comandos (CLI) de Vue.js CLI) y el paquete de módulos y la herramienta de compilación muy potentes [paquete web] (https://webpack.js.org/). Ambas herramientas se basan en el tiempo de ejecución Nodo.js y su administrador de paquetes, npm. Si aún no ha instalado el nodo, consulte los documentos de instalación de Node.js para su sistema, que también incluirá una instalación de npm.

Instale Vue.js CL (vue-cli):

1
$ npm install vue-cli -g

Ahora, con la CLI instalada, la usaré para inicializar una aplicación Vue.js SPA. La CLI hace lo siguiente:

  1. Instalar y configurar webpack para agrupar mi código
  2. Instale un servidor de desarrollo con recarga en caliente (el servidor se reinicia automáticamente cuando se cambia un archivo)
  3. Agregue una dependencia para vue-router
  4. Despliegue una estructura básica de archivos Vue.js SPA

Primero creo una carpeta de alto nivel que contendrá todo el código para este tutorial llamado "encuesta". A continuación, creo dos directorios más llamados "frontend" (para Vue.js SPA) y "backend" (para desarrollar la API REST), luego cambio mi directorio de trabajo al directorio frontend.

1
2
3
4
5
$ mkdir survey
$ cd survey
$ mkdir frontend
$ mkdir backend
$ cd frontend

Ahora la verdadera magia. Se ingresa el comando de inicialización de la CLI de Vue, que luego me pide que responda una serie de preguntas.

Presione Intro para aceptar los valores predeterminados para las preguntas (i) Nombre del proyecto, (ii) Descripción del proyecto, (iii) Autor del proyecto, (iv) Construcción independiente. Cuando se le solicite instalar vue-router, ingrese "Y" para que sí. Ingrese "n" para las entradas restantes y acepte los valores predeterminados.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
$ vue init webpack survey-spa

? Project name survey-spa
? Project description A Vue.js project
? Author Adam McQuistan <[correo electrónico protegido]>
? Vue build standalone
? Install vue-router? No
? Set up unit tests No
? Setup e2e tests with Nightwatch? No
? Should we run `npm install` for you after the project has been created? (recommended) npm

   vue-cli · Generated "survey-spa".


# Installing project dependencies ...
...

Ahora debería haber un nuevo directorio llamado "survey-spa". Cambie los directorios a este directorio y emita un comando npm para compilar el proyecto e iniciar el servidor de desarrollo.

1
2
$ cd survey-spa
$ npm run dev

Ahora puedo ingresar http://localhost:8080 en la ventana de mi navegador y debería ver la página de plantilla repetitiva de Vue.js similar a la que se muestra a continuación.

Vue.js template page{.img-responsive}

La estructura de archivos que se creó se parece a la que se muestra a continuación. He omitido a propósito el atolladero de tonterías dentro de la carpeta node_modules.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
survey-spa/
├── README.md
├── build
   ├── build.js
   ├── check-versions.js
   ├── logo.png
   ├── utils.js
   ├── vue-loader.conf.js
   ├── webpack.base.conf.js
   ├── webpack.dev.conf.js
   └── webpack.prod.conf.js
├── config
   ├── dev.env.js
   ├── index.js
   └── prod.env.js
├── index.html
├── package-lock.json
├── package.json
├── src
   ├── App.vue
   ├── assets
      └── logo.png
   ├── components
      └── HelloWorld.vue
   ├── main.js
   └── router
       └── index.js
└── static

Es probable que esto parezca un poco abrumador las primeras veces que lo mire, pero no temas, solo necesitamos preocuparnos por los archivos en el directorio src/, más el archivo index.html. Por supuesto, los otros archivos son importantes y tal vez algún día averigüe para qué se usan, pero por ahora simplemente ignóralos.

Los archivos bajo el directorio src/ son donde escribiré el código para impulsar la funcionalidad de la aplicación. Abramos estos archivos y tengamos una idea de lo que está pasando.

índice.html

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <title>survey-spa</title>
  </head>
  <body>
    <div id="app"></div>
    <!-- built files will be auto injected -->
  </body>
</html>

Este es el único archivo HTML que utiliza Vue SPA y rara vez contiene mucho más de lo que se muestra arriba, con la excepción de que a veces se vinculará a marcos CSS y otras bibliotecas de JavaScript dentro de este archivo. El único elemento div que se produce con un id predeterminado de "app" es a lo que se adjuntará la instancia principal de Vue. Ese objeto Vue inyecta el HTML y el CSS que se encuentran en los componentes, que se analizarán más adelante, en el div para producir la interfaz de usuario.

principal.js

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.

import Vue from 'vue'
import App from './App'
import router from './router'

Vue.config.productionTip = false

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  components: { App },
  template: '<App/>'
})

El archivo main.js es el punto de entrada principal para la aplicación y es donde registrará la instancia de Vue y las extensiones como vue-router y vuex. Como puede ver, aquí es donde reside la instancia de Vue. La instancia se registra en la aplicación div discutida anteriormente, además se alimenta el objeto del enrutador y el componente App de alto nivel.

vista.de.aplicación

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<template>
  <div id="app">
    <img src="./assets/logo.png">
    <router-view/>
  </div>
</template>

<script>
export default {
  name: 'App'
}
</script>

<style>
#app {
  font-family: 'Avenir', Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-align: center;
  color: #2c3e50;
  margin-top: 60px;
}
</style>

El archivo App.vue sirve como componentes de la aplicación de nivel superior y, a menudo, contiene el diseño general de la aplicación. Los componentes de Vue tienen una estructura específica que contiene una sección <template> para HTML específico del componente, una sección <script> para definir el objeto Vue y los comportamientos de ese componente implementados en JavaScript, y un <styles > sección para reglas CSS / SCSS. Sin embargo, ese último bit puede ser un poco confuso porque, de forma predeterminada, las reglas de estilo que define en un componente no solo pertenecen a ese componente. En realidad, afectan a todos los elementos en todo el proyecto a menos que agregue un atributo alcance al elemento <estilo>.

enrutador/index.js

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
import Vue from 'vue'
import Router from 'vue-router'
import HelloWorld from '@/components/HelloWorld'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/',
      name: 'HelloWorld',
      component: HelloWorld
    }
  ]
})

El script index.js en el directorio del enrutador es donde se definen y asignan las URL de la aplicación a los componentes. Las dos primeras líneas importan los objetos Vue y Router, que luego se vinculan mediante el método use en el objeto Vue.

La ruta predeterminada que se proporciona desde la plantilla del paquete web vue-cli es simplemente la ruta raíz o de índice para la aplicación, que sirve al componente HelloWorld. Para asignar una ruta de ruta a un componente, primero debe importarse, luego debe definir un objeto de ruta en la matriz routes y darle una ruta, un nombre y el componente que se mostrará.

componentes/HelloWorld.vue

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
<template>
  <div class="hello">
    <h1>{{ msg }}</h1>
    <h2>Essential Links</h2>
    <ul>
      <li>
        <a href="https://vuejs.org" target="_blank">Core Docs</a>
      </li>
      <li>
        <a href="https://forum.vuejs.org" target="_blank">Forum</a>
      </li>
      <li>
        <a href="https://chat.vuejs.org" target="_blank">Community Chat</a>
      </li>
      <li>
        <a href="https://twitter.com/vuejs" target="_blank">Twitter</a>
      </li>
      <br>
      <li>
        <a href="http://vuejs-templates.github.io/webpack/" target="_blank">
          Docs for This Template
        </a>
      </li>
    </ul>
    <h2>Ecosystem</h2>
    <ul>
      <li>
        <a href="http://router.vuejs.org/" target="_blank">vue-router</a>
      </li>
      <li>
        <a href="http://vuex.vuejs.org/" target="_blank">vuex</a>
      </li>
      <li>
        <a href="http://vue-loader.vuejs.org/" target="_blank">vue-loader</a>
      </li>
      <li>
        <a href="https://github.com/vuejs/awesome-vue" target="_blank">
          awesome-vue
        </a>
      </li>
    </ul>
  </div>
</template>

<script>
export default {
  name: 'HelloWorld',
  data() {
    return {
      msg: 'Welcome to Your Vue.js App'
    }
  }
}
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>
h1, h2 {
  font-weight: normal;
}
ul {
  list-style-type: none;
  padding: 0;
}
li {
  display: inline-block;
  margin: 0 10px;
}
a {
  color: #42b983;
}
</style>

El directorio "components" es donde residen los componentes de la interfaz de usuario. El componente ‘HelloWorld’ de arriba nuevamente contiene la plantilla de tres secciones básicas, el script y el estilo, que tienen algún contenido de ejemplo de la plantilla de inicialización de vue-cli.

Eche un vistazo a los contenidos de la sección de secuencias de comandos. Aquí verá que se está exportando un objeto. Este objeto se inyectará en la instancia Vue que se inicializó en el archivo main.js. Dentro de este objeto JavaScript hay un método data que devuelve un objeto. Este objeto es donde puede colocar el estado de nivel de componente (datos) y, en este ejemplo, es una propiedad única llamada msg.

Puede acceder y mostrar el estado de su componente por su nombre de propiedad dentro del HTML en la sección de plantilla. En el ejemplo proporcionado, verá esto como {{ msg }}. Los corchetes dobles son la sintaxis de plantilla predeterminada para realizar la interpolación de texto y están inspirados en el sistema de plantilla Bigote. Cada vez que desee mostrar datos en el HTML de su componente, envuélvalo entre corchetes dobles.

Aportando algo de estilo

Para darle a esta aplicación un poco más de atractivo, usaré el marco CSS de Bulma. El objetivo de este tutorial no será cómo usar Bulma, pero aun así quiero incluirlo para evitar el aspecto monótono del HTML sin estilo.

De vuelta en la terminal en el mismo directorio que el archivo package.json, instale y guarde bulma en el proyecto con el siguiente comando:

1
$ npm install --save bulma

Además, tendré que instalar algunas herramientas de desarrollo para cargar correctamente los estilos de la aplicación para que los componentes sepan cómo trabajar con ellos. Para hacer esto, npm instala estos paquetes adicionales.

1
2
3
4
$ npm install --save-dev vue-style-loader
$ npm install --save-dev css-loader
$ npm install --save-dev sass-loader
$ npm install --save-dev node-sass

Ahora abra App.vue y reemplace la sección de estilo con lo que se muestra a continuación, que importará el marco de bulma usando la sintaxis de importación scss.

1
2
3
<style lang="scss">
@import '~bulma/bulma'
</style>

Dale una página de inicio

Bien, ahora que tenemos una comprensión básica de la estructura y las partes principales de una aplicación Vue.js SPA, puedo comenzar a escribir código.

Comience cambiando el nombre del archivo HelloWorld.vue a Home.vue y luego borre el contenido de las secciones de plantilla, secuencia de comandos y estilo. Además, en App.vue elimine la línea del logotipo de la imagen de Vue <img src="./assets/logo.png"> y elimine el contenido del elemento <style> mientras está allí. Por último, abra router/index.js e importe el componente Home.vue en lugar de HelloWorld.vue y actualice el objeto de ruta para usar el componente Home.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
import Vue from 'vue'
import Router from 'vue-router'
import Home from '@/components/Home'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/',
      name: 'Home',
      component: Home
    }
  ]
})

Ahora abra el archivo Home.vue y complete la sección del script con lo que se encuentra a continuación.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
export default {
  data() {
    return {
      surveys: [{
      id: 1,
      name: 'Dogs',
      created_at: new Date(2017, 12, 1),
      questions: [
        {
          id: 1,
          text: 'What is your favorite dog?',
          choices: [
            { id: 1, text: 'Beagle', selected: 0 },
            { id: 2, text: 'Labrador', selected: 0 },
            { id: 3, text: 'Rottweiler', selected: 0 }]
        }, {
          id: 2,
          text: 'What is your second favorite dog?',
          choices: [
            { id: 5, text: 'Beagle', selected: 0 },
            { id: 6, text: 'Labrador', selected: 0 },
            { id: 7, text: 'Rottweiler', selected: 0 }]
        }]
      }, {
        id: 2,
        name: 'Cars',
        created_at: new Date(2017, 12, 3),
        questions: [
          {
            id: 5,
            text: 'What is your favorite car?',
            choices: [
              { id: 17, text: 'Corvette', selected: 0 },
              { id: 18, text: 'Mustang', selected: 0 },
              { id: 19, text: 'Camaro', selected: 0 }]
          }, {
            id: 6,
            text: 'What is your second favorite car?',
            choices: [
              { id: 21, text: 'Corvette', selected: 0 },
              { id: 22, text: 'Mustang', selected: 0 },
              { id: 23, text: 'Camaro', selected: 0 }]
          }]
      }]
    }
  }
}

Esto nos da algunos datos ficticios con los que trabajar. Como probablemente te darás cuenta, representa dos encuestas, una sobre perros y otra sobre autos. Los datos proporcionarán el impulso detrás del HTML que estamos a punto de escribir al proporcionar contenido para mostrar.

Ahora, en la sección de plantilla, agregaré un div que envolverá todos mis otros elementos. Cada componente de Vue debe tener un solo elemento principal, no puede haber elementos hermanos de nivel superior o el componente no se compilará. Dentro de este div agregaré una sección para Bulma encabezado de héroe.

Debajo del encabezado habrá otra sección para mostrar el nombre de cada encuesta y la fecha en que se creó. Es en este bloque de HTML donde comenzaremos a ver algunas de las maravillas que proporciona Vue.js.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
<template>
<div>
  <section class="hero is-primary">
    <div class="hero-body">
      <div class="container has-text-centered">
        <h2 class="title">Check out recent surveys</h2>
      </div>
    </div>
  </section>
  <section class="section">
    <div class="container">
      <div class="card" v-for="survey in surveys" v-bind:key="survey.id">
        <div class="card-content">
          <p class="title">{{ survey.name}}</p>
          <p class='subtitle'>{{ survey.created_at.toDateString() }}</p>
        </div>
      </div>
    </div>
  </section>
</div>
</template>

Guarde los archivos no guardados en el proyecto y actualice su navegador, que ahora debería aparecer como se muestra a continuación:

Survey cards{.img-responsive}

Como puede ver en la captura de pantalla, se muestran dos tarjetas de encuesta de Bulma. Estas dos encuestas se asignan a la matriz de objetos de encuesta que estaban en mi función de datos de mi componente Inicio, que alimenté en mi HTML usando la directiva v-for.

Eche un vistazo nuevamente a la siguiente subsección del código de la plantilla original, que representa una encuesta. Este elemento completo y sus hijos se repiten una vez para cada encuesta en la matriz surveys. Básicamente, los datos impulsan la generación de HTML.

La parte v-bind:key agrega un atributo llamado key igual a la identificación de la encuesta a cada div con clase "card". Vue usa estas claves para realizar un seguimiento explícito de cada nodo que se crea en el DOM, lo que ayuda en la contabilidad y el rendimiento. Se recomienda establecer siempre una clave única para el elemento más externo que se utiliza junto con una directiva v-for.

1
2
3
4
5
6
<div class="card" v-for="survey in surveys" v-bind:key="survey.id">
    <div class="card-content">
      <p class="title">{{ survey.name}}</p>
      <p class='subtitle'>{{survey.created_at.toDateString()}}</p>
    </div>
</div>

La directiva v-for usa una sintaxis de elemento en elementos donde elementos es un iterable como una matriz o las propiedades de un objeto y elemento es un alias para cada elemento en el iterable. Sin embargo, existen variaciones de esta sintaxis, lo que permite una mayor flexibilidad y control.

Por ejemplo, supongamos que tenía una serie de letras var letras = ['a', 'd', 'a', 'm'] que quería usar para impulsar la creación de una lista desordenada HTML ole regular que muestra cada letra y su índice correspondiente. Bueno, eso podría hacerse con esta variación de v-for:

1
2
3
4
5
  <ul>
    <li v-for="(letter, i) in letters" v-bind:key="i">
      Index position {{ i }} has letter {{ letter }}
    </li>
  </ul>

Dando como resultado el siguiente resultado:

1
2
3
4
 Index position 0 has letter a
 Index position 1 has letter d
 Index position 2 has letter a
 Index position 3 has letter m

Para iterar sobre las propiedades de un objeto, la sintaxis es bastante similar. Dado un objeto como var persona = { nombre: 'adam', ocupación: 'desarrollador de software', residencia: 'lincoln, nebraska' }, la iteración con una directiva v-for se vería así:

1
2
3
4
5
  <ul>
    <li v-for="(value, key) in person" v-bind:key=key>
      key -> {{ key }}, value -> {{ value }}
    </li>
  </ul>
1
2
3
 key -> name, value -> adam
 key -> occupation, value -> software developer
 key -> residence, value -> lincoln, nebraska

Simulacro de una solicitud AJAX para encuestas

Tengo mi primer componente de interfaz de usuario funcional que muestra una colección de encuestas, pero al final la aplicación real deberá obtener datos de encuestas de nuestra API REST. Para hacer esto un poco más realista, me gustaría simular las funciones de una solicitud AJAX para alimentar las encuestas del componente Inicio.

En el directorio src, cree una nueva carpeta llamada "api" y luego agregue un script llamado index.js dentro de ella. Aquí es donde me burlaré de mis funciones AJAX. En este nuevo archivo, corte y pegue la matriz surveys del componente Home.vue como una constante global.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
// api/index.js

const surveys = [{
  id: 1,
  name: 'Dogs',
  created_at: new Date(2018, 1, 1),
  questions: [{
    id: 1,
    text: 'What is your favorite dog?',
    choices: [
      { id: 1, text: 'Beagle', selected: 0 },
      { id: 2, text: 'Labrador', selected: 0 },
      { id: 3, text: 'Rottweiler', selected: 0 }]
  }, {
    id: 2,
    text: 'What is your second favorite dog?',
    choices: [
      { id: 5, text: 'Beagle', selected: 0 },
      { id: 6, text: 'Labrador', selected: 0 },
      { id: 7, text: 'Rottweiler', selected: 0 }]
  }]
}, {
  id: 2,
  name: 'Cars',
  created_at: new Date(2018, 1, 3),
  questions: [{
    id: 5,
    text: 'What is your favorite car?',
    choices: [
      { id: 17, text: 'Corvette', selected: 0 },
      { id: 18, text: 'Mustang', selected: 0 },
      { id: 19, text: 'Camaro', selected: 0 }]
  }, {
    id: 6,
    text: 'What is your second favorite car?',
    choices: [
      { id: 21, text: 'Corvette', selected: 0 },
      { id: 22, text: 'Mustang', selected: 0 },
      { id: 23, text: 'Camaro', selected: 0 }]
  }]
}]

Debajo de esta matriz de encuestas, cree una función llamada fetchSurveys que devuelve una promesa con la matriz de encuestas después de esperar 300 milisegundos (para simular el retraso de la API). Será necesario exportar la función para poder acceder a ella desde el componente “Inicio”.

1
2
3
4
5
6
7
export function fetchSurveys() {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(surveys)
    }, 300)
  })
}

De vuelta en la función de datos del componente Home, inicialice la propiedad surveys en una matriz vacía e importe la función fetchSurveys dentro de la sección del script.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
<script>
import { fetchSurvey } from '@/api'
export default {
 data() {
    return {
      surveys: []
    }
  }
}
</script>

Los componentes de Vue tienen una serie de etapas de ciclo de vida definidas que son significativas para el desarrollador cuando hace varias cosas, como extraer datos mediante una solicitud AJAX. Para alimentar los datos de la encuesta en el componente ‘Inicio’, tendré que conectarme a una de las etapas del ciclo de vida de Vue, específicamente la etapa ‘antes del montaje’. Hay varias otras etapas que son útiles para muchas más cosas además de las solicitudes de AJAX, pero me remito a los Documentos de Vue.js oficiales ) para una explicación detallada.

La etapa del ciclo de vida beforeMount funciona bien para la llamada a la API porque se ejecuta justo antes de que comience el montaje de nuestro componente, y justo antes de que se llame a render en nuestro componente. Esto le da tiempo para obtener datos antes de mostrarlos al usuario.

Para aprovechar la etapa beforeMount del componente Home todo lo que necesito hacer es agregarlo como un nuevo método al objeto Vue del componente. Dentro de esta función haré una llamada a mi función fetchSurveys y asignaré las encuestas devueltas a la propiedad data de las encuestas.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
<script>
import { fetchSurveys } from '@/api'
export default {
  data() {
    return {
      surveys: []
    }
  },
  beforeMount() {
    fetchSurveys().then(response => {
      this.surveys = response
    })
  }
}
</script>

Guardar todos los archivos en el proyecto y actualizar el navegador ahora me da la misma página de inicio que vimos anteriormente, pero ahora con una llamada AJAX simulada.

Recursos

¿Desea obtener más información sobre Vue.js y la creación de aplicaciones web front-end? Intente consultar algunos de los siguientes recursos para profundizar en este marco de front-end:

Conclusión

Esta publicación ha cubierto los aspectos básicos de la configuración de una aplicación Vue.js SPA con vue-cli usando la plantilla del paquete web. Además de la configuración del proyecto, cubrí cómo usar los datos en forma de un iterable para generar dinámicamente contenido de UI usando la poderosa directiva v-for Vue.js. Para el último tema importante, toqué las etapas del ciclo de vida de los componentes y cómo la etapa beforeMount puede ser útil para cargar datos en un componente con una solicitud AJAX simulada.

En la próxima publicación, cubriré cómo usar la extensión vue-router para fluir de una página a otra, lo que le dará a nuestra aplicación un concepto de flujo de trabajo. El código de este tutorial se puede encontrar en mi cuenta de GitHub que contiene una rama para cada publicación. Gracias por leer y no dude en comentar o criticar a continuación.