Cómo racionalizar su proceso de desarrollo React.js usando Webpack 4

Foto original en: https://www.instagram.com/p/BiaH379hrAp/?taken-by=riittagirl

En el mundo real del desarrollo, tenemos que agregar nuevas características muy rápidamente. En este tutorial, le mostraré todo lo que puede hacer para optimizar este proceso y alcanzar el 120% de su velocidad de desarrollo.

¿Por qué, podrías preguntar?

Porque hacer trabajo manual es extremadamente contraproducente en lo que respecta a la programación. Queremos automatizar tanto como sea posible. Así que le mostraré qué partes del proceso de desarrollo con React podemos ajustar usando Webpack v4.6.0.

No cubriré los primeros pasos para configurar la configuración del paquete web, ya que ya lo hice en mi publicación anterior. Allí, describí cómo configurar Webpack con mayor detalle. Asumiré que ya está familiarizado con los conceptos básicos de configuración de Webpack, por lo que podemos comenzar con una configuración lista.

Configurar Webpack

En su webpack.config.js, ingrese el siguiente código:

// webpack v4
const path = require ('ruta');
const HtmlWebpackPlugin = require ('html-webpack-plugin');
const WebpackMd5Hash = require ('webpack-md5-hash');
const CleanWebpackPlugin = require ('clean-webpack-plugin');
module.exports = {
  entrada: {main: './src/index.js'},
  salida: {
    ruta: ruta.resolver (__ dirname, 'dist'),
    nombre de archivo: '[nombre]. [chunkhash] .js'
  },
  módulo: {
    reglas: [
      {
        prueba: /\.js$/,
        excluir: / node_modules /,
        utilizar: {
          cargador: "babel-loader"
        }
      }
    ]
  },
  complementos: [
    nuevo CleanWebpackPlugin ('dist', {}),
    nuevo HtmlWebpackPlugin ({
      inyectar: ​​falso
      hash: cierto
      plantilla: './src/index.html',
      nombre de archivo: 'index.html'
    }),
    nuevo WebpackMd5Hash ()
  ]
};

y en tu package.json:

{
 "nombre": "publicación",
 "versión": "1.0.0",
 "descripción": "",
 "main": "index.js",
 "guiones": {
  "build": "paquete web - producción en modo",
  "dev": "paquete web - desarrollo de modo"
 },
  "autor": "",
 "licencia": "ISC",
 "devDependencies": {
    "babel-cli": "^ 6.26.0",
    "babel-core": "^ 6.26.0",
    "babel-loader": "^ 7.1.4",
    "babel-preset-env": "^ 1.6.1",
    "babel-preset-react": "^ 6.24.1",
    "babel-runtime": "^ 6.26.0",
    "clean-webpack-plugin": "^ 0.1.19",
    "html-webpack-plugin": "^ 3.2.0",
    "reaccionar": "^ 16.3.2",
    "react-dom": "^ 16.3.2",
    "webpack": "^ 4.6.0",
    "webpack-cli": "^ 2.0.13",
    "webpack-md5-hash": "0.0.6"
  }
}

Ahora puede descargar sus módulos de nodo:

npm i

y agregue la carpeta src / a su proyecto con index.html e index.js

Primero en src / index.html:


  
  
  
    
       

y luego en src / index.js:

console.log ("hola, mundo");

Ejecutemos el script de desarrollo:

npm run dev

Ahí lo tienes: ¡compilado! Ahora configuremos React para ello también.

Configurar su proyecto React

Como React usa una sintaxis especial llamada JSX, necesitamos transpilar nuestro código. Si vamos al sitio web de babel, tiene el valor predeterminado para Reaccionar.

npm install --save-dev babel-cli babel-preset-react

Nuestro archivo .babelrc debería verse así:

{
  "presets": ["env", "react"]
}

Agregue un poco de inicialización de la aplicación a su index.js:

importar Reaccionar desde 'reaccionar';
importar {render} desde 'react-dom';
La aplicación de clase extiende React.Component {
render () {
    regreso (
      
        '¡Hola Mundo!'       
    );   } }
render (, document.getElementById ('aplicación'));

y ejecuta el script de desarrollo:

npm run dev

Si logró generar una carpeta ./dist con index.html y un archivo principal con un hash, ¡lo hizo genial! ¡Tenemos nuestra aplicación compilando!

Configurar web-dev-server

Técnicamente, no tenemos que hacer esto, ya que existen muchos servidores basados ​​en nodos para aplicaciones front-end. Pero recomiendo webpack-dev-server porque está diseñado para funcionar con Webpack, y es compatible con un montón de características interesantes, como el reemplazo de módulos activos, mapas de origen, etc.

Como mencionan en la página de documentación oficial:

Use webpack con un servidor de desarrollo que proporcione recarga en vivo. Esto debe usarse solo para el desarrollo.

Aquí es donde puede ser un poco confuso: ¿cómo hacer que webpack-dev-server solo funcione para el modo dev?

npm i webpack-dev-server --save-dev

en su package.json, ajuste

"guiones": {
  "dev": "webpack-dev-server --mode development --open",
  "build": "paquete web - producción en modo"
}

Ahora debería iniciar un servidor y abrir automáticamente la pestaña de su navegador con su aplicación.

Su package.json se ve así en este punto:

{
 "Nombre": "publicación",
 "Versión": "1.0.0",
 "Descripción": "",
 "Main": "index.js",
 "guiones": {
   "dev": "webpack-dev-server --mode development --open",
   "build": "paquete web - producción en modo"
 },
 "Autor": "",
 "Licencia": "ISC",
 "DevDependencies": {
   "Babel-cli": "6.26.0",
   "Babel-core": "6.26.0",
   "Babel-loader": "7.1.4",
   "Babel-preset-env": "1.6.1",
   "Babel-preset-react": "6.24.1",
   "Babel-runtime": "6.26.0",
   "Clean-webpack-plugin": "0.1.19",
   "Html-webpack-plugin": "3.2.0",
   "Reaccionar": "16.3.2",
   "React-dom": "16.3.2",
   "Paquete web": "4.6.0",
   "Webpack-cli": "2.0.13",
   "Webpack-dev-server": "3.1.3",
   "Webpack-md5-hash": "0.0.6"
 }
}

Ahora, si intenta modificar algo en su aplicación, el navegador debería actualizar automáticamente la página.

Luego, debe descargar React devtools como una extensión de Chrome.

De esta forma, puede depurar su aplicación desde la consola de Chrome mucho más fácilmente.

Configuración de ESLint

¿Por qué lo necesitamos? Bueno, generalmente no tenemos que usarlo. Pero ESLint es una herramienta útil. En nuestro caso, representará nuestro código (en el editor y terminal, y en el navegador) y resaltará nuestros errores, errores tipográficos y errores si tenemos alguno. Esto se llama linting.

ESLint es una utilidad de código abierto de JavaScript creada originalmente por Nicholas C. Zakas en junio de 2013. Existen alternativas, pero hasta ahora funciona muy bien con ES6 y React, encuentra problemas comunes y se integra con otras partes del ecosistema.

Por ahora, vamos a instalarlo localmente para nuestro nuevo proyecto. Por supuesto, ESLint en este punto tiene una gran cantidad de configuraciones. Puedes leer más sobre ellos en el sitio web oficial.

npm install eslint --save-dev
./node_modules/.bin/eslint --init

El último comando creará un archivo de configuración. Se le pedirá que elija entre tres opciones:

En este tutorial, elegí el primero: responder preguntas. Aquí están mis respuestas:

Esto agregará el archivo .eslintrc.js al directorio de su proyecto. Mi archivo generado se ve así:

module.exports = {
    "env": {
        "navegador": verdadero,
        "commonjs": cierto,
        "es6": verdadero
    },
    "extend": "eslint: recomendado",
    "parserOptions": {
        "ecmaFeatures": {
            "experimentalObjectRestSpread": verdadero,
            "jsx": verdadero
        },
        "sourceType": "módulo"
    },
    "complementos": [
        "reaccionar"
    ],
    "reglas": {
        "sangría": [
            "error",
            4 4
        ],
        "estilo de salto de línea": [
            "error",
            "unix"
        ],
        "citas": [
            "error",
            "soltero"
        ],
        "semi": [
            "error",
            "siempre"
        ]
    }
};

Nada pasa hasta ahora. Aunque esta es una configuración perfectamente válida, no es suficiente; tenemos que integrarla con Webpack y nuestro editor de texto para que funcione. Como mencioné, podemos tenerlo en el editor de código, terminal (como un linter) o como un gancho de precompromiso. Lo configuraremos para nuestro editor por ahora.

Configuración para el código de Visual Studio

En caso de que se lo pregunte, ESLint tiene un complemento para casi todos los principales editores de código, incluidos Visual Studio Code, Visual Studio, SublimeText, Atom, WebStorm e incluso vim. Así que adelante y descargue la versión para su propio editor de texto. Usaré VS Code en esta demostración.

Ahora podemos ver aparecer algunos errores de código. Esto se debe a que el proyecto tiene un archivo de configuración que alinea el código y se queja cuando no se obedecen algunas reglas.

Puede depurarlo manualmente verificando el mensaje de error, o puede aprovecharlo y simplemente presionar guardar y automáticamente arreglará las cosas.

Ahora puede ir y ajustar la configuración de ESLint:

module.exports = {
    "env": {
        "navegador": verdadero,
        "commonjs": cierto,
        "es6": verdadero
    },
    "extiende": ["eslint: recomendado", "complemento: reaccionar / recomendado"],
    "parserOptions": {
        "ecmaFeatures": {
            "experimentalObjectRestSpread": verdadero,
            "jsx": verdadero
        },
        "sourceType": "módulo"
    },
    "complementos": [
        "reaccionar"
    ],
    "reglas": {
        "sangría": [
            "error",
            2
        ],
        "estilo de salto de línea": [
            "error",
            "unix"
        ],
        "citas": [
            "advertir",
            "soltero"
        ],
        "semi": [
            "error",
            "siempre"
        ]
    }
};

Esto no interrumpirá la compilación si incluyó comillas dobles por error en lugar de comillas simples. También agregará algunas comprobaciones para JSX.

Añadir más bonita

Prettier es uno de los formateadores más populares hoy en día, y es bien aceptado por la comunidad de codificación. Puede agregarse a ESLint, su editor, y también instalarse como un enlace previo al compromiso.

Lo instalaré en mi código VS aquí

Una vez que lo instale, puede intentar verificar su código nuevamente. Si escribimos una sangría extraña y presionamos guardar, debería formatear automáticamente el código ahora.

Eso no es suficiente todavía. Para que ESLint funcione sincronizado y no emita los mismos errores dos veces, o incluso tenga conflictos de reglas, debe integrarlo con su ESLint.

npm i --save-dev prettier eslint-plugin-prettier

En los documentos oficiales, recomiendan que uses hilo, pero npm lo hará por ahora. Agregue a su archivo .eslintrc.json:

...
  sourceType: "módulo"
},
complementos: ["reaccionar", "más bonito"],
se extiende: ["eslint: recomendado", "complemento: reaccionar / recomendado"],
reglas: {
  guión: ["error", 2],
  "linebreak-style": ["error", "unix"],
  comillas: ["advertir", "sencillo"],
  semi: ["error", "siempre"],
  "prettier / prettier": "error"
}
...

Ahora queremos ampliar nuestras reglas de ESLint para incluir reglas más bonitas:

npm i --save-dev eslint-config-prettier

y agregue algunas extensiones a su configuración de eslint:

...
se extiende: [
  "eslint: recomendado",
  "complemento: reaccionar / recomendado",
  "más bonita",
  "complemento: más bonito / recomendado"
]
...

Agreguemos algunas configuraciones más. Debe hacer esto para evitar desajustes entre las reglas Prettier predeterminadas y sus reglas ESLint, como la que tengo ahora:

Prettier toma prestado el formato de anulación de ESLint. Esto le permite aplicar la configuración a archivos específicos.

Ahora puede crear un archivo de configuración en forma de archivo .js.

nano prettier.config.js

Ahora, pegue en ese archivo:

module.exports = {
  ancho de impresión: 80,
  tabWidth: 2,
  semi: cierto,
  singleQuote: verdadero,
  bracketSpacing: verdadero
};

Ahora, cuando presione Guardar, verá que su código se formatea automáticamente. ¿No es así más bonita? Juego de palabras muy intencionado.

Mi package.json se ve así:

{
 "nombre": "publicación",
 "versión": "1.0.0",
 "descripción": "",
 "main": "index.js",
 "guiones": {
  "build": "paquete web - producción en modo",
  "dev": "webpack-dev-server --mode development --open"
 },
 "autor": "",
 "licencia": "ISC",
 "devDependencies": {
  "babel-cli": "^ 6.26.0",
  "babel-core": "^ 6.26.0",
  "babel-loader": "^ 7.1.4",
  "babel-preset-env": "^ 1.6.1",
  "babel-preset-react": "^ 6.24.1",
  "babel-runtime": "^ 6.26.0",
  "clean-webpack-plugin": "^ 0.1.19",
  "eslint": "^ 4.19.1",
  "eslint-config-prettier": "^ 2.9.0",
  "eslint-plugin-prettier": "^ 2.6.0",
  "eslint-plugin-react": "^ 7.7.0",
  "html-webpack-plugin": "^ 3.2.0",
  "más bonita": "^ 1.12.1",
  "reaccionar": "^ 16.3.2",
  "react-dom": "^ 16.3.2",
  "webpack": "^ 4.6.0",
  "webpack-cli": "^ 2.0.13",
  "webpack-dev-server": "^ 3.1.4",
  "webpack-md5-hash": "0.0.6"
 }
}

Ahora que tenemos todo esto configurado, recapitulemos rápidamente: ESLint vigila su código en busca de errores, y Prettier es una herramienta de formato de estilo. ESLint tiene muchas más formas de detectar errores, mientras que Prettier formatea bien su código.

// webpack v4
const path = require ('ruta');
const HtmlWebpackPlugin = require ('html-webpack-plugin');
const WebpackMd5Hash = require ('webpack-md5-hash');
const CleanWebpackPlugin = require ('clean-webpack-plugin');
module.exports = {
  entrada: {main: './src/index.js'},
  salida: {
    ruta: ruta.resolver (__ dirname, 'dist'),
    nombre de archivo: '[nombre]. [chunkhash] .js'
  },
  módulo: {
    reglas: [
      {
        prueba: /\.js$/,
        excluir: / node_modules /,
        utilizar: {
          cargador: "babel-loader"
        }
      }
    ]
  },
  complementos: [
    nuevo CleanWebpackPlugin ('dist', {}),
    nuevo HtmlWebpackPlugin ({
      inyectar: ​​falso
      hash: cierto
      plantilla: './src/index.html',
      nombre de archivo: 'index.html'
    }),
    nuevo WebpackMd5Hash ()
  ]
};

Problema: Prettier no formatea automáticamente el código en Visual Studio Code

Algunas personas han señalado que VS Code no funciona con Prettier.

Si su complemento Prettier no formatea el código automáticamente al guardar, puede arreglarlo agregando este código a la configuración del Código VS:

"[javascript]": {
    "editor.formatOnSave": verdadero
  }

como se describe aquí.

Agregar el cargador ESLint a su tubería

Como ESLint está configurado en el proyecto, también se quejará en su terminal una vez que ejecute el servidor de desarrollo.

Nota: Aunque es posible hacerlo, en este momento no recomiendo usar ESLint como cargador. Romperá la configuración del mapa fuente, que describí con mayor detalle en mi artículo anterior Cómo resolver los problemas de Webpack. El caso práctico. Mostraré cómo configurarlo aquí, en caso de que los chicos ya hayan solucionado el error que tenían.

Webpack tiene su propio cargador ESLint.

npm install eslint-loader --save-dev

Debe agregar ESLint a las reglas. Cuando se utiliza con cargadores transpiling (como babel-loader), asegúrese de que estén en el orden correcto (de abajo hacia arriba). De lo contrario, los archivos serán verificados después de ser procesados ​​por babel-loader

...
módulo: {
  reglas: [
    {
      prueba: /\.js$/,
      excluir: / node_modules /,
      uso: [{loader: "babel-loader"}, {loader: "eslint-loader"}]
    }
  ]
},
...

Aquí hay algunos posibles problemas que puede tener:

  • agregue una variable no utilizada a su archivo de índice

Si tropieza con este error (no-unused-vars), está bastante bien explicado en este problema en GitHub y aquí.

Podemos resolver este problema agregando algunas reglas, explicadas aquí y aquí.

Como habrás notado, obtienes el error no vars no utilizado aquí. Debe hacer que sea una advertencia y no un error, porque de esta manera es mucho más fácil hacer un desarrollo rápido. Debe agregar una nueva regla a su ESLint para que no obtenga el error predeterminado.

Puede leer más sobre esta configuración aquí y aquí.

...
semi: ['error', 'siempre'],
'no-no-vars': [
  'advertir',
  {vars: 'all', args: 'none', ignoreRestSiblings: false}
],
'prettier / prettier': 'error'
}
...

De esta forma obtendremos mensajes de error y advertencia bonitos.

Me gusta la idea de tener una función de reparación automática, pero seamos claros: no soy el mayor fanático de que las cosas cambien mágicamente. Para evitar esa situación, podemos comprometer autofix por ahora.

Gancho previo al compromiso

Las personas generalmente son muy cuidadosas cuando se trata de usar herramientas Git. Pero te aseguro que este es muy fácil y directo. Los ganchos de confirmación previa con Prettier se usan para que los equipos tengan un estilo de base de código coherente en todos los archivos de proyecto, y nadie puede confirmar código sin estilo. Configure la integración de Git para su proyecto de esta manera:

git init
git add.
nano .gitignore (agregue allí sus módulos_nodo)
git commit -m "Primera confirmación"
git remote add origin tu origen
git push -u maestro de origen

Aquí hay algunos excelentes artículos sobre git hooks y el uso de Prettier.

Para las personas que dicen que solo puedes hacerlo localmente, ¡no, eso no es cierto!

Puede hacerlo utilizando la herramienta pelusa de este repositorio de Andrey Okonetchnikov.

Agregar propTypes

Vamos a crear un nuevo componente en nuestra aplicación. Hasta ahora, nuestro index.js se ve así:

importar Reaccionar desde 'reaccionar';
importar {render} desde 'react-dom';
La aplicación de clase extiende React.Component {
  render () {
    return 
Hola
;   } } render (, document.getElementById ('aplicación'));

Crearemos un nuevo componente llamado Hello.js para fines de demostración.

importar Reaccionar desde 'reaccionar';
clase Hello extiende React.Component {
  render () {
    return 
{this.props.hello}
;   } } Exportar predeterminado Hola;

Ahora impórtelo a su archivo index.js:

importar Reaccionar desde 'reaccionar';
importar {render} desde 'react-dom';
importar Hola desde './Hola';
La aplicación de clase extiende React.Component {
  render () {
    regreso (
      
            
   );   } } render (, document.getElementById ('aplicación'));

Se suponía que íbamos a ver el elemento, pero ESLint se queja:

Error: [eslint] 'hola' falta en la validación de accesorios (react / prop-types)

En React v16, es obligatorio agregar tipos de accesorios para evitar la confusión de tipos. Puedes leer más sobre esto aquí.

importar Reaccionar desde 'reaccionar';
importar PropTypes desde 'prop-types';
clase Hello extiende React.Component {
  render () {
    return 
{this.props.hello}
;   } } Hola.propTypes = {   hola: PropTypes.string }; Exportar predeterminado Hola;

Reemplazo de módulo caliente

Ahora que ha verificado su código, es hora de agregar más componentes a su aplicación React. Hasta ahora solo tienes dos, pero en la mayoría de los casos tienes docenas.

Por supuesto, recompilar toda la aplicación al actualizar cada vez que cambie algo en su proyecto no es una opción. Necesitas una forma más rápida de hacerlo.

Así que agreguemos un reemplazo de módulo activo, también conocido como HMR. En la documentación, se describe como:

Hot Module Replacement (HMR) intercambia, agrega o elimina módulos mientras se ejecuta una aplicación, sin una recarga completa. Esto puede acelerar significativamente el desarrollo de varias maneras:
Conservar el estado de la aplicación que se pierde durante una recarga completa.
Ahorre un valioso tiempo de desarrollo actualizando solo lo que ha cambiado.
Ajusta el estilo más rápido, casi comparable a los estilos cambiantes en el depurador del navegador.

No voy a entrar en los tecnicismos de cómo funciona aquí: ese sería el tema de una publicación separada. Pero aquí está cómo configurarlo:

...
salida: {
  ruta: ruta.resolver (__ dirname, 'dist'),
  nombre de archivo: '[nombre]. [chunkhash] .js'
},
devServer: {
  contentBase: './dist',
  caliente: cierto
},
módulo: {
  reglas: [
...

Resolver pequeños problemas con HMR

Tuvimos que reemplazar chunkhash con hash, porque evidentemente webpack ha solucionado ese problema desde la última vez. ¡Ahora tenemos el reemplazo del módulo caliente funcionando!

...
module.exports = {
   entrada: {main: './src/index.js'},
   salida: {
     ruta: ruta.resolver (__ dirname, 'dist'),
     nombre de archivo: '[nombre]. [hash] .js'
   },
   devServer: {
     contentBase: './dist',
...

Resolviendo errores

Si ejecutamos el script de desarrollo aquí:

luego use consejos de este problema para solucionarlo.

A continuación, agregue el indicador activo al script de desarrollo en package.json:

...
"guiones": {
   "build": "paquete web - producción en modo",
   "dev": "webpack-dev-server --hot"
}
...

Mapas de origen:

Como mencioné anteriormente, los mapas fuente no funcionarán junto con el cargador ESLint. He presentado un problema aquí.

Por lo general, no los querría en su proyecto de todos modos (ya que desea depurar su proyecto a partir de mensajes de error de ESLint). También son conocidos por hacer que HMR sea más lento.

Puedes leer más aquí y aquí.

Pero si de todos modos desea mapas de origen, la forma más fácil de agregarlos es a través de la opción devtools.

...
module.exports = {
  entrada: {main: './src/index.js'},
  salida: {
    ruta: ruta.resolver (__ dirname, 'dist'),
    nombre de archivo: '[nombre]. [hash] .js'
  },
  devtool: 'inline-source-map',
  devServer: {
    contentBase: './dist',
    caliente: cierto
  },
  ...

Nota: los mapas de origen no funcionarán hasta que especifique el entorno de la manera correcta. Puedes leer sobre mi proceso de depuración aquí. A continuación, le proporcionaré un spoiler y una explicación de cómo resolví ese problema.

Si ahora vamos y creamos un error en nuestro código, esto se mostrará en la consola y nos indicará el lugar correcto:

... o eso pensamos. Pero no:

Ese es el comportamiento de la rana

Necesita cambiar la variable de entorno de esta manera:

...
"main": "index.js",
"guiones": {
  "build": "webpack --mode = production",
  "start": "NODE_ENV = desarrollo webpack-dev-server --mode = desarrollo --hot"
},
"autor": ""
...

webpack.config.js

...
devtool: 'inline-source-map',
devServer: {
  contentBase: './dist',
  abierto: verdadero
}
...

¡Ahora funciona!

Como puede ver, ¡apuntamos al archivo exacto donde ocurrió el error!

¡Ahora ha configurado con éxito el entorno de desarrollo para su proyecto!

Recapitulemos:

  • Configuramos webpack
  • Creamos nuestro primer componente React
  • Incluimos ESLint para verificar errores en el código
  • Configuramos el reemplazo del módulo caliente
  • Nosotros (tal vez) agregamos mapas fuente

Nota: dado que muchas dependencias npm pueden cambiar para cuando lea esto, la misma configuración podría no funcionar para usted. Le pido amablemente que deje sus errores en los comentarios a continuación para poder editarlos más tarde.

¡Suscríbete y aplaude por este artículo! ¡Gracias!

Más materiales: