¿Viniendo de Github? Se puede tener una mejor experiencia de visualización de este tutorial en el sitio a continuación: https://pokedpeter.dev
Este tutorial le mostrará cómo construir un proyecto de nodo Barebones (JavaScript) desde cero con las siguientes golosinas:
Requisitos previos:
Establezcamos un proyecto de nodo Barebones
Crea nuestro proyecto de nodo. Puede omitir todas las opciones de inmediato.
mkdir project
cd project
npm init Un archivo llamado package.json se configurará con las opciones que eligió. Puede omitir las opciones de interfaz e ir con los valores predeterminados ejecutando npm init -y
{
"name" : " project " ,
"version" : " 1.0.0 " ,
"description" : " " ,
"main" : " index.js " ,
"scripts" : {
"test" : " echo " Error: no test specified " && exit 1 "
},
"author" : " " ,
"license" : " ISC "
}El script ejecutable principal no se crea automáticamente. Cúbrelo.
touch index.js Ponga algo básico en index.js para fines de prueba.
console . log ( 'Hello World' ) ;Pruébelo desde la CLI:
node index.js
Que le da una salida de consola:
Hello World
JavaScript no viene con las bibliotecas estándar incorporadas. El enfoque recomendado es instalar paquetes NPM. Probemos un ejemplo. Instalaremos LODASH, una popular biblioteca de útiles utilidades.
npm install lodash
Aquí está la salida:
added 1 package, and audited 4 packages in 987ms
found 0 vulnerabilities
Ahora que hemos intallado a Lodash, ahora podemos usarlo en nuestra aplicación. Abra index.js nuevamente y actualice para que coincida:
const _ = require('lodash);
console.log(_.snakeCase('Hello World'));
Ejecutarlo y verá la siguiente salida:
hello_world
Vea el archivo package.json nuevamente y observe la sección de nuevas dependencies con la entrada de LOdash:
"dependencies" : {
"lodash" : " ^4.17.21 "
}Consejo
Para ver rápidamente el contenido del archivo de la CLI, escriba: cat package.json
Vea los archivos de su proyecto y observe que se ha creado una carpeta node_modules :
$ ls -l
index.js
node_modules
package-lock.json
package.jsonEsta carpeta es donde se almacenan sus dependencias. Vamos a verlos:
$ ls node_modules
@types lodash typescriptAgregamos TypeScript a nuestro proyecto de nodo Barebones.
Instale la dependencia de TypeScript, como una depedencia de desarrollo. Todas las dependencias de mecanografiado solo se requieren durante el desarrollo, por lo que lo hacemos --save-dev
npm install --save-dev typescriptInstalar definiciones de tipo TypeScript para nodo:
npm install --save-dev @types/nodeConsejo
Instale múltiples paquetes de una vez combinándolos en una sola línea: npm install --save-dev typescript @types/node
Eche un vistazo a las dependencias en package.json . Aquí está la porción relevante:
{
"devDependencies" : {
"@types/node" : " ^20.4.9 " ,
"typescript" : " ^5.1.6 "
}
}Inicializar TypeScript ejecutando el siguiente comando en cualquier lugar dentro de su proyecto.
npx tsc --init Esto creará un archivo tsconfig.json con la configuración predeterminada:
Created a new tsconfig.json with:
target: es2016
module: commonjs
strict: true
esModuleInterop: true
skipLibCheck: true
forceConsistentCasingInFileNames: true
Utilizamos npx que ejecuta binarios instalados localmente que se han instalado a través de package.json .
Advertencia
Algunas guías de instalación recomendarán instalar TypeScript globalmente sudo npm install -g typescript . Recomendaría instalar una versión local (es decir, dentro de la carpeta de su proyecto)
La versión global puede terminar diferiendo de la versión local instalada para su proyecto. Ejecutar tsc utiliza directamente la versión global. Cuando tsc se ejecuta como parte de NPM en su proyecto, utiliza la versión local.
Hay varias opciones establecidas de forma predeterminada en tsconfig.json . Hay muchas opciones comentadas, no se muestran a continuación.
{
"compilerOptions" : {
/* Visit https://aka.ms/tsconfig.json to read more about this file */
/* Basic Options */
"target" : " es5 " , /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', or 'ESNEXT'. */
"module" : " commonjs " , /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */
/* Strict Type-Checking Options */
"strict" : true , /* Enable all strict type-checking options. */
/* Module Resolution Options */
"esModuleInterop" : true , /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */
/* Advanced Options */
"skipLibCheck" : true , /* Skip type checking of declaration files. */
"forceConsistentCasingInFileNames" : true /* Disallow inconsistently-cased references to the same file. */
}
}Algunos ajustes recomendados a los valores predeterminados:
"target" : " es2015 " , // I'd recommend es2015 at a minimum. es5 is ancient.
"outDir" : " build " , // Keep our compiled javascript in the build directory
"rootDir" : " src " , // Keep our source code in a separate directory
"noImplicitAny" : true , // We're using Typescript yeah? And not adding Typescript to an existing project. Enforce good habits from the start.
"lib" : [ " es2020 " ], // Setting this excludes DOM typings as we are using Node. Otherwise you'll run into errors declaring variables like 'name' Con respecto al target . En general, las versiones más nuevas del nodo admitirán las características de ECMA más nuevas. El siguiente sitio web es un gran recurso para ver qué características de ECMA están disponibles para cada versión de Node:
https://node.green/
Ya no hay necesidad de index.js:
rm index.jsConfigurar nuestro código fuente del proyecto:
mkdir src
cd src
touch index.ts Agregue algo básico al index.ts para probarlo:
console . log ( 'Hello typescript!' ) ;Compile nuestro proyecto Barebones.
npx tsc La salida compilada, como JavaScript, se puede encontrar en el directorio /build . Contendrá index.js reflejando nuestro src/index.ts
Contenido de index.js:
"use strict" ;
console . log ( 'Hello World!' ) ;¡Ahora está listo para crear proyectos JavaScript con TypeScript!
Hasta hace poco, TSLINT era el Linter de código TypeScript, pero ahora está en desuso ya que el proyecto se ha consolidado en Eslint. Aquí está la página de inicio oficial:
Sitio web:
https://eslint.org
El sitio de Github:
https://github.com/typescript-eslint/typescript-eslint
Instale Eslint (como dependencia del desarrollo, por supuesto)
npm install --save-dev eslintConfigurar nuestra configuración de pelusa usando el comando init de Eslint:
npx eslint --initSigue las indicaciones. Estamos utilizando el nodo, por lo que no se requiere soporte de navegador. Le preguntará si desea instalar los complementos TypeScript dependientes. Adelante y haz eso.
✔ How would you like to use ESLint ? · problems
✔ What type of modules does your project use ? · esm
✔ Which framework does your project use ? · none
✔ Does your project use TypeScript ? · No / Yes
✔ Where does your code run ? · node
✔ What format do you want your config file to be in ? · JSON
The config that you ' ve selected requires the following dependencies:
@typescript-eslint/eslint-plugin@latest @typescript-eslint/parser@latest
✔ Would you like to install them now with npm? · No / Yes
Successfully created .eslintrc.json file in /your/projectMás información sobre la configuración de la pelusa a continuación:
https://eslint.org/docs/user-guide/configurating
Usando las opciones seleccionadas anteriormente, nuestro archivo .eslintrc.json se ve así:
{
"env" : {
"es2020" : true ,
"node" : true
},
"extends" : [
" eslint:recommended " ,
" plugin:@typescript-eslint/recommended "
],
"parser" : " @typescript-eslint/parser " ,
"parserOptions" : {
"ecmaVersion" : 11 ,
"sourceType" : " module "
},
"plugins" : [
" @typescript-eslint "
],
"rules" : {
}
}Es posible que haya notado que una de las preguntas durante el proceso de inicio de Eslint fue este:
? How would you like to use ESLint ? …
To check syntax only
▸ To check syntax and find problems
To check syntax, find problems, and enforce code styleLa última opción también hace cumplir un estilo de código. Si selecciona esa opción, una pregunta de seguimiento será:
? How would you like to define a style for your project ? …
▸ Use a popular style guide
Answer questions about your style
Inspect your JavaScript file(s)Si opta por usar una guía de estilo popular, tendrá una opción de lo siguiente:
? Which style guide do you want to follow ? …
▸ Airbnb: https://github.com/airbnb/javascript
Standard: https://github.com/standard/standard
Google: https://github.com/google/eslint-config-google
XO: https://github.com/xojs/eslint-config-xoRecomiendo investigar las guías de estilo anteriores y optar por una que se alinee con sus preferencias.
A continuación, crearemos otro archivo de configuración en el texto de la demanda para permitirnos excluir archivos y directorios de la pelusa:
touch .eslintignoreY agregue el siguiente contenido al archivo:
node_modules
build
No queremos que las pelusas en nuestro código JavaScript compilado.
Por defecto, las reglas estándar están habilitadas. Vea los elementos marcados en la lista en:
https://eslint.org/docs/rules/
Por ejemplo, intentemos romper la regla no-extra-semi .
Intente agregar un semi-colon al final de la línea en index.ts y haga la verificación de pelusa para ver un error:
console . log ( 'Hello typescript' ) ; ;Y luego:
npx eslint srcQue resulta en:
1:34 error Unnecessary semicolon @typescript-eslint/no-extra-semi
✖ 1 problem (1 error, 0 warnings)
1 error and 0 warnings potentially fixable with the `--fix` option.
Advertencia
Al instalar la opción Airbnb, he notado que Eslint necesita tener la extensión del archivo .ts aprobado:
npx eslint src --ext .ts Cree un script para esto en el package.json para que podamos llamarlo convenientemente:
"scripts" : {
...
"lint" : " eslint src --ext .ts "
},Aplicable solo cuando esté en NPM <V7, pero tenga en cuenta que si se ejecuta el script y los problemas de NPM, verá el siguiente mensaje de error de NPM agregado debajo de la salida de Eslint:
> eslint src --ext .ts
/home/user/dev/test/src/index.ts
1:1 warning Unexpected console statement no-console
1:21 error Missing whitespace after semicolon semi-spacing
1:22 error Unnecessary semicolon no-extra-semi
✖ 3 problems (2 errors, 1 warning)
2 errors and 0 warnings potentially fixable with the ` --fix ` option.
npm ERR ! code ELIFECYCLE
npm ERR ! errno 1
npm ERR ! [email protected] lint: ` eslint src --ext .ts `
npm ERR ! Exit status 1
npm ERR !
npm ERR ! Failed at the [email protected] lint script.
npm ERR ! This is probably not a problem with npm. There is likely additional logging output above.
npm ERR ! A complete log of this run can be found in:
npm ERR ! /home/user/.npm/_logs/2021-08-18T15_27_55_318Z-debug.logNo veo el error NPM cuando está en NPM V7 (por ejemplo, cuando uso el nodo 16.6.2)
Cada regla puede ser uno de los tres estados:
| Modo de regla | Descripción |
|---|---|
| 0 o "APAGADO" | Deshabilita la regla |
| 1 o "advertir" | ADVERTENCIA, Linter no fallará |
| 2 o "error" | Error, el Linter fallará |
Las reglas se pueden agregar como claves para un objeto de reglas en el archivo de configuración de la pelusa .eslintrc.json:
{
"root" : true ,
"parser" : " @typescript-eslint/parser " ,
"plugins" : [ ... ],
"extends" : [ ... ],
"rules" : {
..your rules go here..
}
}Encuentre reglas en eslint.org:
https://eslint.org/docs/rules/
Probemos la regla estilística llamada 'coma-dangle'. Queremos advertir al usuario si le falta una matriz con varias líneas en el último elemento.
Agregue la regla:
"rules" : {
"comma-dangle" : [
" warn " , {
"arrays" : " always-multiline "
}
]
}Lea los detalles de la regla en el sitio web. Hay bastante personalización permitida para muchas reglas. Queremos cubrir las comas colgantes en todos los escenarios en este ejemplo.
Cambiar index.ts con el siguiente código:
const movies = [
'Lord of the Flies' ,
'Battle Royale'
] ;
movies . pop ( ) ;Ejecute el enlace:
npx eslint srcAhora deberíamos ver la siguiente advertencia:
3:18 warning Missing trailing comma comma-dangle
✖ 1 problem (0 errors, 1 warning)
0 errors and 1 warning potentially fixable with the ` --fix ` option. Nota En la salida hay una opción para solucionar el problema. Intente ejecutar el enlace con la opción --fix :
npx eslint --fix src Esta vez no hay salida de la punta y si verificamos index.ts veremos que la coma colgante se ha agregado automáticamente:
const movies = [
'Lord of the Flies' ,
'Battle Royale' , // <-- dangling comma added
] ;
movies . pop ( ) ; Usaremos el código más bonito para formatear. Es un formateador de código obstinado que admite muchos idiomas, incluidos TypeScript, JavaScript y otros formatos que puede usar para configuraciones como JSON y YAML.
https://prettier.io
Alternativamente, puede quedarse con Eslint para formatear estilísticamente su código. La más bonita se diferencia en que no modifica su código, a menos que establezca una de las pequeñas opciones.
Instale el módulo:
npm install --save-dev prettierCrea el archivo de configuración. Esto le permite a los editores y otras herramientas saber que está utilizando Prettier:
echo {} > .prettierrc.jsonProbablemente no necesite agregar ninguna opción al archivo de configuración, ya que la mayoría implicará transformar su código. Lo mejor es que eso sea de Eslint y simplemente deje que más bonito lidie con el formato.
Crea un archivo Ignore. Esto le permite a la CLI y los editores más bonitos saber qué archivos excluir del formato.
touch .prettierignore Agregue las siguientes líneas a .prettierignore :
node_modules
buildPrueba más bonita con el siguiente comando. No expondrá nada simplemente emitir el código formateado:
npx prettier srcBasado en nuestro último cambio a index.ts, la salida será:
const movies = [ "Lord of the Flies" , "Battle Royale" ] ;
movies . pop ( ) ;Podemos ver que la matriz de múltiples líneas se ha formateado en una sola línea.
Escriba los cambios en el archivo repitiendo el comando con la opción --write :
npx prettier --write srcEsto enumerará los archivos que se han formateado:
src/index.ts 279msDado el código de formato de Eslint y Prettier Can, puede esperar que ocurran algunos conflictos. Prettier ha creado reglas específicamente para Eslint que básicamente deshabilita cualquier regla que sea innecesaria o conflictiva cuando se combinan con más bonitas.
El primero es eslint-config-prettier :
https://github.com/prettier/eslint-config-prettier
Esta configuración apaga todas las reglas que son innecesarias o en conflicto con más bonitas. Instálelo con el siguiente comando:
npm install --save-dev eslint-config-prettier Luego, agréguelo a la última línea de su sección extends en la configuración de Eslint, .eslintrc.json :
{
"extends" : [
"eslint:recommended" ,
"plugin:@typescript-eslint/recommended" ,
"plugin:@typescript-eslint/eslint-recommended" ,
"prettier" // <-- Add this
] ,
}Puede ejecutar el siguiente comando en cualquier archivo para verificar que no hay conflicto entre Eslint y Prettier:
npx eslint-config-prettier src/index.tsSi todo va bien, debe obtener la siguiente respuesta:
No rules that are unnecessary or conflict with Prettier were found. El siguiente para instalar es eslint-plugin-prettier :
https://github.com/prettier/eslint-plugin-prettier
Se ejecuta más bonitos como una regla de Eslint e informa las diferencias como problemas individuales de eslint. Instálelo con el siguiente comando:
npm install --save-dev eslint-plugin-prettier Luego actualice su archivo .eslintrc.json de la siguiente manera:
{
"plugins" : [ " prettier " ],
"rules" : {
"prettier/prettier" : " error "
}
}Busque el siguiente complemento:
ESLint - por Dirk Baeumer
Busque el siguiente complemento:
Prettier - Code formatter - por Prettier
Presione Ctrl + Shift + I al código de formato. Se le pedirá que seleccione el formateador predeterminado. Seleccione Prettier como su valor predeterminado.
Busque el siguiente complemento:
Prettier ESLint - por Rebecca chaleco
Estos scripts están adaptados a nuestro proyecto TypeScript. Solo estamos revisando los archivos .ts.
Agregue los comandos a continuación a la sección scripts de su package.json .
"start:dev" : " nodemon " "lint" : " eslint --ext .ts src "
"lint-fix" : " eslint --fix --ext .ts src " "pretty" : " prettier --write 'src/**/*.ts' " Curveball es un marco micro para construir API en el nodo. Está construido desde cero con soporte para TypeScript en lugar de su predecesor más popular KOA.
https://curveballjs.org/
Instalarlo:
npm install @curveball/core Copie el ejemplo del sitio web en index.ts . Lo único que cambiaremos es el número de puerto. Por dos razones. Uno, el puerto 80 puede estar bloqueado. Dos. Ejecutar en diferentes puertos nos permite tener múltiples proyectos de nodo que se ejecutan simultáneamente.
import { Application } from '@curveball/core' ;
const app = new Application ( ) ;
app . use ( async ctx => {
ctx . response . type = 'text/plain' ;
ctx . response . body = 'hello world' ;
} ) ;
app . listen ( 9000 ) ;Inicie el servidor en modo dev con el script que creamos anteriormente:
npm run start:devObtendrá la siguiente salida como nodemon escucha a los cambios de archivo:
> [email protected] start:dev /home/your_name/project
> nodemon
[nodemon] 2.0.4
[nodemon] to restart at any time, enter ` rs `
[nodemon] watching path(s): src/ ** / *
[nodemon] watching extensions: ts,jsDespués de hacer un cambio de código, mire la salida de la consola del servidor para que sea Nodemon en el trabajo. También actualice la página web para ver actualizaciones.
Configure la recarga automática después de los cambios de código para el desarrollo. Instale nodemon para monitorear los cambios de archivo y ts-node para ejecutar el código TypeScript directamente en lugar de tener que compilar y luego pasar al node .
npm install --save-dev ts-node nodemon Agregue una configuración nodemon.json . Esto configurará Nodemon para observar los cambios en archivos .ts y .js dentro de su directorio de código fuente y luego ejecutará el comando EXEC después de los cambios.
{
"watch" : [ " src " ],
"ext" : " .ts,.js " ,
"ignore" : [],
"exec" : " ts-node ./src/index.ts "
} Agregue un script NPM dentro de package.json para comenzar nodemon para el desarrollo:
"start:dev" : " nodemon " Ejecute npm run start:dev para iniciar el proceso de recarga.
Instale instrucciones de Docker y de búsqueda sobre cómo ejecutar Docker sin sudo: las instrucciones omitidas aquí, ya que son específicas de OS / Distro.
Cree un archivo docker-compose.yml con un solo contenedor de nodo como servicio:
El nombre de nuestro proyecto es "Proyecto" como es el nombre del servicio y el contenedor. Tenemos un volumen de mapeo de nuestro directorio de proyecto a /proyecto dentro del contenedor de nodo. Por último, asegúrese de que los puertos coincidan con los puertos expuestos en su solicitud.
Más detalles a continuación:
https://docs.docker.com/Compose/Compose-File/
version : ' 3 '
services :
project :
build : .
container_name : project
volumes :
- .:/project
ports :
- " 9000 " A continuación, cree Dockerfile con los siguientes contenidos.
FROM node:12
WORKDIR /project
COPY package.json .
RUN npm install
COPY . .
CMD [ "npm" , "run" , "start:dev" ]Esto establece nuestro directorio de proyectos dentro del contenedor, instala nuestros paquetes de nodos, copia el contenido de nuestro sistema de archivos nativo e inicia nuestro servidor Curveball en modo Dev.
Ahora mencione el contenedor:
docker-compose upVerá la siguiente salida:
Creating network "project_default" with the default driver
Building project
Step 1/7 : FROM node:12
---> dfbb88cfffc8
Step 2/7 : WORKDIR /project
---> Running in 86fff3a3c90b
Removing intermediate container 86fff3a3c90b
---> 5912fd119492
Step 3/7 : COPY package.json .
---> 4fa4df04cc6b
Step 4/7 : RUN npm install
---> Running in 8b814e4d75d2
...
(Node package installation happens here)
...
Removing intermediate container 8b814e4d75d2
---> 3bfd2b1a83e4
Step 5/7 : COPY . .
---> f6971fdf7fb5
Step 6/7 : EXPOSE 9000
---> Running in 2ab0a152b0a6
Removing intermediate container 2ab0a152b0a6
---> 0e883b79c1b3
Step 7/7 : CMD ["npm", "run", "start:dev"]
---> Running in f64884ae2643
Removing intermediate container f64884ae2643
---> 1abb8edf6373
Successfully built 1abb8edf6373
Successfully tagged project_project:latest
WARNING: Image for service project was built because it did not already exist. To rebuild this image you must use `docker-compose build` or `docker-compose up --build`.
Creating project ...
Creating project ... done
Attaching to project
project |
project | > [email protected] start:dev /project
project | > nodemon
project |
project | [nodemon] 2.0.4
project | [nodemon] to restart at any time, enter `rs`
project | [nodemon] watching path(s): src/**/*
project | [nodemon] watching extensions: ts,js
project | [nodemon] starting `ts-node ./src/index.ts`
Puede usar CTRL-C para detener el contenedor.
Use docker-compose up -d para elevar el contenedor en modo separado: se menciona en el pez parada y puede continuar usando la línea de comando.
Estamos creando un contenedor basado en el nodo V12. Nuestro directorio de trabajo dentro del contenedor se define como /project (donde se asignará nuestro código de proyecto)
La versión del nodo instalado dependerá del sistema operativo instalado y qué tan actualizados están sus paquetes.
Si usa el nodo fuera de los contenedores Docker y trabaja en múltiples proyectos de nodos, cada uno que requieren diferentes versiones de nodo, instale NVM:
https://github.com/nvm-sh/nvm
Muchas gracias a lo siguiente por ayudarme a crear este tutorial.