Projetos TypeScript
O gerador de projetos TypeScript pode ser usado para criar uma biblioteca ou aplicação TypeScript moderna configurada com as melhores práticas, como ECMAScript Modules (ESM), referências de projeto do TypeScript, Vitest para executar testes e Biome para linting e formatação.
Gerar um Projeto TypeScript
Seção intitulada “Gerar um Projeto TypeScript”Você pode gerar um novo projeto TypeScript de duas maneiras:
pnpm nx g @aws/nx-plugin:ts#projectyarn nx g @aws/nx-plugin:ts#projectnpx nx g @aws/nx-plugin:ts#projectbunx nx g @aws/nx-plugin:ts#projectVocê também pode realizar uma execução simulada para ver quais arquivos seriam alterados
pnpm nx g @aws/nx-plugin:ts#project --dry-runyarn nx g @aws/nx-plugin:ts#project --dry-runnpx nx g @aws/nx-plugin:ts#project --dry-runbunx nx g @aws/nx-plugin:ts#project --dry-run- Instale o Nx Console VSCode Plugin se ainda não o fez
- Abra o console Nx no VSCode
- Clique em
Generate (UI)na seção "Common Nx Commands" - Procure por
@aws/nx-plugin - ts#project - Preencha os parâmetros obrigatórios
- Clique em
Generate
| Parâmetro | Tipo | Padrão | Descrição |
|---|---|---|---|
| name Obrigatório | string | - | Nome do projeto TypeScript |
| directory | string | packages | Diretório pai onde a biblioteca é colocada. |
| subDirectory | string | - | O subdiretório onde a biblioteca é colocada. Por padrão, este é o nome da biblioteca. |
| preferInstallDependencies | boolean | true | Se deve preferir instalar dependências após a execução do gerador. Defina como false para adiar a instalação ao executar múltiplos geradores em lote (uma instalação ainda é executada se necessário para que geradores subsequentes possam calcular o grafo de projetos Nx); instale uma vez no final. |
Saída do Gerador
Seção intitulada “Saída do Gerador”O gerador criará a seguinte estrutura de projeto no diretório <directory>/<name>:
Directorysrc Código-fonte TypeScript
- index.ts
- package.json Manifesto do projeto definindo o nome do pacote e dependências do projeto
- project.json Configuração do projeto e alvos de build
- tsconfig.json Configuração base do TypeScript para este projeto (estende o tsconfig.base.json da raiz do workspace)
- tsconfig.lib.json Configuração do TypeScript para sua biblioteca (seu código-fonte de runtime ou empacotado)
- tsconfig.spec.json Configuração do TypeScript para seus testes
- vitest.config.mts Configuração para o Vitest
Você também notará algumas mudanças nos seguintes arquivos na raiz do seu workspace:
- nx.json A configuração do Nx é atualizada para configurar o plugin @nx/js/typescript para o seu projeto
- tsconfig.base.json um alias do TypeScript é configurado para o seu projeto para que ele possa ser importado por outros projetos no seu workspace
- tsconfig.json uma referência de projeto do TypeScript é adicionada para o seu projeto
Escrevendo Código-Fonte TypeScript
Seção intitulada “Escrevendo Código-Fonte TypeScript”Adicione seu código TypeScript no diretório src.
Sintaxe de Importação ESM
Seção intitulada “Sintaxe de Importação ESM”Como seu projeto TypeScript é um ES Module, certifique-se de escrever suas declarações de importação com a sintaxe ESM correta, referenciando explicitamente a extensão do arquivo:
import { sayHello } from './hello.js';Exportando para Outros Projetos TypeScript
Seção intitulada “Exportando para Outros Projetos TypeScript”O ponto de entrada para o seu projeto TypeScript é src/index.ts. Você pode adicionar exportações aqui para qualquer coisa que você gostaria que outros projetos pudessem importar:
export { sayHello } from './hello.js';export * from './algorithms/index.js';Importando o Código da Sua Biblioteca em Outros Projetos
Seção intitulada “Importando o Código da Sua Biblioteca em Outros Projetos”Aliases do TypeScript para o seu projeto são configurados no tsconfig.base.json do workspace, o que permite que você referencie seu projeto TypeScript de outros projetos TypeScript:
import { sayHello } from '@my-scope/my-library';Quando você adiciona uma declaração de importação para um novo projeto no seu workspace pela primeira vez, você provavelmente verá um erro no seu IDE semelhante ao abaixo:
Erro de importação
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)Isso ocorre porque uma referência de projeto ainda não foi configurada, e o projeto importado ainda não foi declarado como uma dependência do workspace no package.json do seu projeto.
Seu workspace está configurado com geradores de sincronização que gerenciam ambos para você, então você não precisa configurá-los manualmente. Simplesmente execute o seguinte comando e o Nx adicionará a configuração necessária:
pnpm nx syncyarn nx syncnpx nx syncbunx nx sync 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!O gerador de sincronização do TypeScript do Nx adiciona a referência do projeto, e o gerador ts#sync do plugin declara o projeto importado no package.json do seu projeto (workspace:* onde o gerenciador de pacotes suporta o protocolo workspace, * no npm e yarn classic), para que o gerenciador de pacotes vincule o projeto local na instalação. Depois disso, o erro no seu IDE deve desaparecer e você está pronto para usar sua biblioteca.
Mantendo os Aliases de Caminho Sincronizados
Seção intitulada “Mantendo os Aliases de Caminho Sincronizados”Se você adicionar entradas personalizadas de compilerOptions.paths no tsconfig.json de um projeto, o TypeScript para de herdar os aliases do workspace definidos em tsconfig.base.json. O gerador oculto ts#sync é executado antes do alvo compile (configurado em nx.json) para copiar quaisquer aliases base ausentes nos arquivos tsconfig.json, tsconfig.lib.json e tsconfig.app.json que já declaram paths. Para desativar, remova @aws/nx-plugin:ts#sync de targetDefaults.compile.syncGenerators em nx.json.
Dependências
Seção intitulada “Dependências”Cada projeto TypeScript declara suas dependências de runtime de terceiros em seu próprio package.json. Ferramentas de build e teste compartilhadas entre projetos são definidas no package.json raiz.
Para adicionar uma dependência de runtime a um projeto, instale-a nesse projeto:
pnpm add some-npm-package --filter my-libraryyarn workspace @my-scope/my-library add some-npm-packagenpm install --legacy-peer-deps some-npm-package -w packages/my-librarybun add some-npm-package --cwd packages/my-libraryVocê também pode executar o comando simples add/install do seu gerenciador de pacotes de dentro do diretório do projeto.
Para adicionar uma ferramenta de desenvolvimento compartilhada, instale-a na raiz do workspace:
pnpm add -Dw some-dev-toolyarn add -D some-dev-toolnpm install --legacy-peer-deps -D some-dev-toolbun add -D some-dev-toolCatálogos
Seção intitulada “Catálogos”Para gerenciadores de pacotes que suportam catálogos (pnpm, yarn e bun), os geradores registram cada versão no catálogo e a referenciam com o protocolo catalog: (por exemplo, "zod": "catalog:"), então o catálogo é a única fonte de verdade para versões, independentemente de qual projeto declara a dependência. Isso ajuda você a seguir uma política de versão única, evitando conflitos de tipo e múltiplas cópias de pacotes em bundles de implantação.
Quando você adicionar uma nova dependência por conta própria, mantenha-a no catálogo também:
O workspace define catalogMode: strict, então pnpm add registra a versão no catálogo e a referencia automaticamente — sem etapas extras.
pnpm add some-npm-package --filter my-libraryO protocolo catalog: do yarn apenas referencia uma entrada de catálogo existente — ele não pode criar uma — então registre a versão primeiro.
-
Adicione a versão sob
catalogem.yarnrc.yml:.yarnrc.yml catalog:some-npm-package: ^1.0.0 -
Referencie-a do projeto:
Terminal window yarn workspace @my-scope/my-library add some-npm-package@catalog:
O protocolo catalog: do bun apenas referencia uma entrada de catálogo existente — ele não pode criar uma — então registre a versão primeiro.
-
Adicione a versão sob
catalognopackage.jsonraiz:package.json {"catalog": {"some-npm-package": "^1.0.0"}} -
Referencie-a do projeto:
Terminal window bun add some-npm-package@catalog: --cwd packages/my-library
Desativando catálogos
Seção intitulada “Desativando catálogos”Os catálogos são habilitados por padrão. Para desativá-los, crie seu workspace com --catalog false:
pnpm create @aws/nx-workspace my-project --catalog falseyarn create @aws/nx-workspace my-project --catalog falsenpm create @aws/nx-workspace -- my-project --catalog falsebun create @aws/nx-workspace my-project --catalog falseOu defina-o em aws-nx-plugin.config.mts a qualquer momento:
export default { packageManager: { catalogs: false, },} satisfies AwsNxPluginConfig;Com os catálogos desabilitados, os geradores escrevem versões de dependências diretamente no package.json de cada projeto, e manter as versões alinhadas entre projetos é sua responsabilidade.
Declarando todas as dependências na raiz
Seção intitulada “Declarando todas as dependências na raiz”Se você preferir declarar todas as dependências apenas no package.json raiz (sem declarações de dependências por projeto), desative a regra de lint no biome.json do workspace:
{ "linter": { "rules": { "correctness": { "noUndeclaredDependencies": "off" } } }}Os projetos resolvem pacotes instalados na raiz no momento do build, então tudo ainda é construído — você abre mão de manifestos por projeto como um registro preciso das dependências de cada projeto (o que importa se você posteriormente publicar um projeto ou dividir o repositório).
Código de Runtime
Seção intitulada “Código de Runtime”Quando você usa seu projeto TypeScript como código de runtime (por exemplo, como o handler para uma função AWS Lambda), é recomendado que você use uma ferramenta como Rolldown para empacotar seu projeto, pois isso pode fazer tree-shake para garantir que apenas as dependências que seu projeto realmente referencia sejam incluídas.
Você pode conseguir isso adicionando um alvo como o seguinte ao seu arquivo project.json:
{ ... "targets": { ... "bundle": { "cache": true, "executor": "nx:run-commands", "outputs": ["{workspaceRoot}/dist/packages/my-library/bundle"], "options": { "command": "rolldown -c rolldown.config.ts" } }, },}E adicionando o arquivo rolldown.config.ts da seguinte forma:
import { defineConfig } from 'rolldown';
export default defineConfig([ { input: 'src/index.ts', output: { file: '../../dist/packages/my-library/bundle/index.js', format: 'cjs', codeSplitting: false, }, },]);Seu projeto TypeScript está configurado com um alvo build (definido em project.json), que você pode executar via:
pnpm nx build <project-name>yarn nx build <project-name>npx nx build <project-name>bunx nx build <project-name>Onde <project-name> é o nome totalmente qualificado do seu projeto.
O alvo build irá compilar, fazer lint e testar seu projeto.
A saída do build pode ser encontrada na pasta dist raiz no seu workspace, dentro de um diretório para seu pacote e alvo, por exemplo dist/packages/<my-library>/tsc
Para fazer o build de todos os projetos no seu workspace, execute:
pnpm nx run-many --target buildyarn nx run-many --target buildnpx nx run-many --target buildbunx nx run-many --target buildOu use o comando abreviado:
pnpm buildyarn buildnpm run buildbun buildVitest está configurado para testar seu projeto.
Escrevendo Testes
Seção intitulada “Escrevendo Testes”Os testes devem ser escritos em arquivos .spec.ts ou .test.ts, co-localizados na pasta src do seu projeto.
Por exemplo:
Directorysrc
- hello.ts Código-fonte da biblioteca
- hello.spec.ts Testes para hello.ts
O Vitest fornece sintaxe semelhante ao Jest para definir testes, com utilitários como describe, it, test e expect.
import { sayHello } from './hello.js';
describe('sayHello', () => {
it('should greet the caller', () => { expect(sayHello('Darth Vader')).toBe('Hello, Darth Vader!'); });
});Para mais detalhes sobre como escrever testes e recursos como simular dependências, consulte a documentação do Vitest
Executando Testes
Seção intitulada “Executando Testes”Os testes serão executados como parte do alvo build para o seu projeto, mas você também pode executá-los separadamente executando o alvo test:
pnpm nx test <project-name>yarn nx test <project-name>npx nx test <project-name>bunx nx test <project-name>Você pode executar um teste individual ou conjunto de testes usando a flag -t do Vitest. Passe-a após um separador -- para que o Nx a encaminhe para o Vitest em vez de consumi-la como sua própria opção --target:
pnpm nx test <project-name> -- -t 'sayHello'yarn nx test <project-name> -- -t 'sayHello'npx nx test <project-name> -- -t 'sayHello'bunx nx test <project-name> -- -t 'sayHello'Linting
Seção intitulada “Linting”Os projetos TypeScript usam Biome para linting e formatação. O Biome é configurado no arquivo biome.json da raiz do workspace — alterações nele se aplicam a todos os projetos TypeScript no seu workspace e garantem consistência.
Executando o Linter
Seção intitulada “Executando o Linter”Para invocar o linter para verificar seu projeto, você pode executar o alvo lint.
pnpm nx lint <project-name>yarn nx lint <project-name>npx nx lint <project-name>bunx nx lint <project-name>Corrigindo Problemas de Lint
Seção intitulada “Corrigindo Problemas de Lint”A maioria dos problemas de linting ou formatação pode ser corrigida automaticamente executando com o argumento --configuration=fix.
pnpm nx lint <project-name> --configuration=fixyarn nx lint <project-name> --configuration=fixnpx nx lint <project-name> --configuration=fixbunx nx lint <project-name> --configuration=fixDa mesma forma, se você gostaria de corrigir todos os problemas de lint em todos os pacotes no seu workspace, você pode executar:
pnpm nx run-many --target lint --all --configuration=fixyarn nx run-many --target lint --all --configuration=fixnpx nx run-many --target lint --all --configuration=fixbunx nx run-many --target lint --all --configuration=fixIgnorando Problemas de Lint
Seção intitulada “Ignorando Problemas de Lint”Para evitar que problemas de linting o atrasem durante o desenvolvimento (particularmente se você tiver problemas não corrigíveis automaticamente no seu projeto), você pode executar um build com a configuração skip-lint:
pnpm nx run-many --target build --configuration=skip-lintyarn nx run-many --target build --configuration=skip-lintnpx nx run-many --target build --configuration=skip-lintbunx nx run-many --target build --configuration=skip-lintIsso ignora o alvo de lint inteiramente durante o build.