Ir al contenido

Proyectos de TypeScript

El generador de proyectos TypeScript se puede utilizar para crear una biblioteca o aplicación moderna TypeScript configurada con mejores prácticas como Módulos ECMAScript (ESM), referencias de proyecto de TypeScript, Vitest para ejecutar pruebas y Biome para linting y formateo.

Puedes generar un nuevo proyecto TypeScript de dos formas:

  1. Instale el Nx Console VSCode Plugin si aún no lo ha hecho
  2. Abra la consola Nx en VSCode
  3. Haga clic en Generate (UI) en la sección "Common Nx Commands"
  4. Busque @aws/nx-plugin - ts#project
  5. Complete los parámetros requeridos
    • Haga clic en Generate
    ParámetroTipoPredeterminadoDescripción
    name Requeridostring-Nombre del proyecto TypeScript
    directory stringpackagesDirectorio padre donde se coloca la biblioteca.
    subDirectory string-El subdirectorio donde se coloca la biblioteca. Por defecto es el nombre de la biblioteca.
    preferInstallDependencies booleantrueSi se prefiere instalar las dependencias después de que se ejecute el generador. Establecer en false para diferir la instalación al ejecutar múltiples generadores en lote (la instalación aún se ejecuta si es necesaria para que los generadores subsecuentes puedan calcular el grafo de proyectos de Nx); instalar una vez al final.

    El generador creará la siguiente estructura de proyecto en el directorio <directory>/<name>:

    • Directoriosrc Código fuente TypeScript
      • index.ts
    • package.json Manifiesto del proyecto que define el nombre del paquete y las dependencias del proyecto
    • project.json Configuración del proyecto y objetivos de compilación
    • tsconfig.json Configuración base de TypeScript para este proyecto (extiende tsconfig.base.json del workspace)
    • tsconfig.lib.json Configuración TypeScript para tu biblioteca (código en tiempo de ejecución o empaquetado)
    • tsconfig.spec.json Configuración TypeScript para tus pruebas
    • vitest.config.mts Configuración para Vitest

    También notarás cambios en los siguientes archivos en la raíz de tu workspace:

    • nx.json La configuración de Nx se actualiza para configurar el plugin @nx/js/typescript para tu proyecto
    • tsconfig.base.json Se configura un alias TypeScript para tu proyecto permitiendo su importación desde otros proyectos
    • tsconfig.json Se añade una referencia de proyecto TypeScript para tu proyecto

    Añade tu código TypeScript en el directorio src.

    Como tu proyecto TypeScript es un Módulo ES, asegúrate de escribir tus sentencias de importación con la sintaxis ESM correcta, referenciando explícitamente la extensión del archivo:

    index.ts
    import { sayHello } from './hello.js';

    El punto de entrada de tu proyecto TypeScript es src/index.ts. Puedes añadir exports aquí para cualquier elemento que quieras que otros proyectos puedan importar:

    src/index.ts
    export { sayHello } from './hello.js';
    export * from './algorithms/index.js';

    Los alias de TypeScript para tu proyecto están configurados en el tsconfig.base.json del workspace, permitiéndote referenciar tu proyecto TypeScript desde otros proyectos:

    packages/my-other-project/src/index.ts
    import { sayHello } from '@my-scope/my-library';

    Cuando añadas una sentencia de importación para un nuevo proyecto en tu workspace por primera vez, probablemente verás un error en tu IDE similar a este:

    Error de importación
    Ventana de terminal
    File '/path/to/my/workspace/packages/my-library/src/index.ts' is not under 'rootDir' '/path/to/my/workspace/packages/my-consumer'. 'rootDir' is expected to contain all source files.
    File is ECMAScript module because '/path/to/my/workspace/package.json' has field "type" with value "module" ts(6059)
    File '/path/to/my/workspace/packages/my-library/src/index.ts' is not listed within the file list of project '/path/to/my/workspace/packages/my-consumer/tsconfig.lib.json'. Projects must list all files or use an 'include' pattern.
    File is ECMAScript module because '/path/to/my/workspace/package.json' has field "type" with value "module" ts(6307)

    Esto ocurre porque no se ha configurado una referencia de proyecto, y el proyecto importado aún no se ha declarado como dependencia del workspace en el package.json de tu proyecto.

    Tu workspace está configurado con generadores de sincronización que gestionan ambos por ti, por lo que no necesitas configurarlos manualmente. Simplemente ejecuta el siguiente comando y Nx añadirá la configuración requerida:

    Terminal window
    pnpm nx sync
    Ventana de terminal
    NX The workspace is out of sync
    [@nx/js:typescript-sync]: Some TypeScript configuration files are missing project references to the projects they depend on, contain stale project references, or have duplicate project references.
    [@aws/nx-plugin:ts#sync]: Local project dependencies are out of sync. The following workspace dependencies will be declared:
    packages/my-other-project/package.json:
    - @my-scope/my-library: workspace:*
    Syncing the workspace...
    The workspace was synced successfully!

    El generador de sincronización de TypeScript de Nx añade la referencia de proyecto, y el generador ts#sync del plugin declara el proyecto importado en el package.json de tu proyecto (workspace:* donde el gestor de paquetes soporta el protocolo de workspace, * en npm y yarn classic), para que el gestor de paquetes enlace el proyecto local en la instalación. Después de esto, el error en tu IDE debería desaparecer y estarás listo para usar tu biblioteca.

    Manteniendo los alias de rutas sincronizados

    Sección titulada «Manteniendo los alias de rutas sincronizados»

    Si añades entradas personalizadas de compilerOptions.paths en el tsconfig.json de un proyecto, TypeScript deja de heredar los alias del workspace definidos en tsconfig.base.json. El generador oculto ts#sync se ejecuta antes del objetivo compile (configurado en nx.json) para copiar cualquier alias base faltante en los archivos tsconfig.json, tsconfig.lib.json y tsconfig.app.json que ya declaren paths. Para desactivar esta funcionalidad, elimina @aws/nx-plugin:ts#sync de targetDefaults.compile.syncGenerators en nx.json.

    Cada proyecto TypeScript declara sus dependencias de tiempo de ejecución de terceros en su propio package.json. Las herramientas de compilación y prueba compartidas entre proyectos se definen en el package.json raíz.

    Para añadir una dependencia de tiempo de ejecución a un proyecto, instálala en ese proyecto:

    Terminal window
    pnpm add some-npm-package --filter my-library

    También puedes ejecutar el comando add/install simple de tu gestor de paquetes desde dentro del directorio del proyecto.

    Para añadir una herramienta de desarrollo compartida, instálala en la raíz del workspace:

    Terminal window
    pnpm add -Dw some-dev-tool

    Para gestores de paquetes que soportan catálogos (pnpm, yarn y bun), los generadores registran cada versión en el catálogo y la referencian con el protocolo catalog: (ej. "zod": "catalog:"), por lo que el catálogo es la única fuente de verdad para las versiones independientemente de qué proyecto declare la dependencia. Esto te ayuda a seguir una política de versión única, evitando conflictos de tipos y múltiples copias de paquetes en los bundles de despliegue.

    Cuando añadas una nueva dependencia tú mismo, mantenla también en el catálogo:

    El workspace establece catalogMode: strict, por lo que pnpm add registra la versión en el catálogo y la referencia automáticamente — sin pasos adicionales.

    Ventana de terminal
    pnpm add some-npm-package --filter my-library

    Los catálogos están habilitados por defecto. Para desactivarlos, crea tu workspace con --catalog false:

    Terminal window
    pnpm create @aws/nx-workspace my-project --catalog false

    O configúralo en aws-nx-plugin.config.mts en cualquier momento:

    aws-nx-plugin.config.mts
    export default {
    packageManager: {
    catalogs: false,
    },
    } satisfies AwsNxPluginConfig;

    Con los catálogos desactivados, los generadores escriben las versiones de dependencias directamente en el package.json de cada proyecto, y mantener las versiones alineadas entre proyectos es tu responsabilidad.

    Declarando todas las dependencias en la raíz

    Sección titulada «Declarando todas las dependencias en la raíz»

    Si prefieres declarar cada dependencia solo en el package.json raíz (sin declaraciones de dependencias por proyecto), desactiva la regla de lint en el biome.json del workspace:

    biome.json
    {
    "linter": {
    "rules": {
    "correctness": {
    "noUndeclaredDependencies": "off"
    }
    }
    }
    }

    Los proyectos resuelven paquetes instalados en la raíz en tiempo de compilación, por lo que todo sigue compilando — renuncias a los manifiestos por proyecto como un registro preciso de las dependencias de cada proyecto (lo cual importa si luego publicas un proyecto o divides el repositorio).

    Cuando uses tu proyecto TypeScript como código en tiempo de ejecución (por ejemplo como handler para una función AWS Lambda), se recomienda usar una herramienta como Rolldown para empaquetar tu proyecto, ya que puede realizar tree-shake para incluir solo las dependencias realmente usadas.

    Puedes lograr esto añadiendo un objetivo como el siguiente en tu archivo project.json:

    {
    ...
    "targets": {
    ...
    "bundle": {
    "cache": true,
    "executor": "nx:run-commands",
    "outputs": ["{workspaceRoot}/dist/packages/my-library/bundle"],
    "options": {
    "command": "rolldown -c rolldown.config.ts"
    }
    },
    },
    }

    Y añadiendo el archivo rolldown.config.ts de la siguiente forma:

    rolldown.config.ts
    import { defineConfig } from 'rolldown';
    export default defineConfig([
    {
    input: 'src/index.ts',
    output: {
    file: '../../dist/packages/my-library/bundle/index.js',
    format: 'cjs',
    inlineDynamicImports: true,
    },
    },
    ]);

    Tu proyecto TypeScript está configurado con un objetivo build (definido en project.json), que puedes ejecutar mediante:

    Terminal window
    pnpm nx build <project-name>

    Donde <project-name> es el nombre completo de tu proyecto.

    El objetivo build compilará, linteará y probará tu proyecto.

    La salida de compilación se encuentra en la carpeta dist raíz de tu workspace, dentro de un directorio para tu paquete y objetivo, por ejemplo dist/packages/<my-library>/tsc

    Para construir todos los proyectos en tu workspace, ejecuta:

    Terminal window
    pnpm nx run-many --target build

    O usa el comando abreviado:

    Terminal window
    pnpm build

    Vitest está configurado para probar tu proyecto.

    Las pruebas deben escribirse en archivos .spec.ts o .test.ts, ubicados junto al código en la carpeta src de tu proyecto.

    Por ejemplo:

    • Directoriosrc
      • hello.ts Código fuente de la biblioteca
      • hello.spec.ts Pruebas para hello.ts

    Vitest proporciona una sintaxis similar a Jest para definir pruebas, con utilidades como describe, it, test y expect.

    hello.spec.ts
    import { sayHello } from './hello.js';
    describe('sayHello', () => {
    it('debe saludar al llamador', () => {
    expect(sayHello('Darth Vader')).toBe('Hello, Darth Vader!');
    });
    });

    Para más detalles sobre cómo escribir pruebas y características como mock de dependencias, consulta la documentación de Vitest

    Las pruebas se ejecutarán como parte del objetivo build de tu proyecto, pero también puedes ejecutarlas por separado mediante el objetivo test:

    Terminal window
    pnpm nx test <project-name>

    Puedes ejecutar una prueba individual o un conjunto de pruebas usando el flag -t de Vitest. Pásalo después de un separador -- para que Nx lo reenvíe a Vitest en lugar de consumirlo como su propia opción --target:

    Terminal window
    pnpm nx test <project-name> -- -t 'sayHello'

    Los proyectos TypeScript usan Biome para linting y formateo. Biome se configura en el archivo biome.json raíz del workspace — los cambios aquí se aplican a todos los proyectos TypeScript de tu workspace y aseguran consistencia.

    Para invocar el linter y verificar tu proyecto, ejecuta el objetivo lint:

    Terminal window
    pnpm nx lint <project-name>

    La mayoría de problemas de lint o formateo pueden corregirse automáticamente ejecutando con el argumento --configuration=fix.

    Terminal window
    pnpm nx lint <project-name> --configuration=fix

    Similarmente, si quieres corregir todos los problemas de lint en todos los paquetes de tu workspace, puedes ejecutar:

    Terminal window
    pnpm nx run-many --target lint --all --configuration=fix

    Para evitar que los problemas de lint te ralenticen durante el desarrollo (particularmente si tienes problemas no auto-corregibles en tu proyecto), puedes ejecutar una compilación con la configuración skip-lint:

    Terminal window
    pnpm nx run-many --target build --configuration=skip-lint

    Esto omite por completo el objetivo lint durante la compilación.