7.4 KiB
7.4 KiB
AGENTS.md — Guia para Assistentes de IA
Este arquivo descreve os padrões, convenções e arquitetura do projeto
p-comuns. Leia este arquivo antes de sugerir ou gerar qualquer código.
🏗️ Visão Geral do Projeto
p-comuns é um pacote compartilhado (npm monorepo-like) usado como dependência em todos os subprojetos da plataforma e-licencie. Ele provê:
- Tipos TypeScript compartilhados (rotas, filtros, situações, UUIDs...)
- Utilitários de back-end (postgres, cache em memória, dayjs...)
- Utilitários de front-end (Vue 3 + TSX)
- Constantes e enums globais
⚙️ Stack Tecnológica
| Camada | Tecnologia | Versão |
|---|---|---|
| Linguagem | TypeScript | ~5.9.x |
| Runtime (back) | Node.js | ≥20 |
| Framework (front) | Vue 3 | Composition API + <script setup> |
| JSX/TSX | Vue TSX / React-like TSX | via jsxRuntime |
| Linter/Formatter | Biome | 2.4.x |
| Bundler | tsup | 8.x |
| Package manager | pnpm | com workspaces |
| Validação | Zod | 4.x |
| Utilitários de data | dayjs | 1.11.x |
📁 Estrutura do src/
src/
├── index.ts # Entry point — exporta tudo que é público
├── constantes.ts # Constantes globais (enums, valores fixos)
├── situacoes.ts # Status/situações dos processos
├── tipagemRotas.ts # Tipagem forte de rotas da API
├── tipoFiltro.26.ts # Sistema de filtros tipados (operadores PG)
├── uuid.ts # Geração e validação de UUIDs
├── dayjs26.ts # Wrapper do dayjs com locale e plugins
├── extensoes.ts # Extensões de tipos nativos
├── texto_busca.ts # Utilitários de busca em texto
├── variaveisComuns.ts # Variáveis de ambiente compartilhadas
├── postgres.ts # Cliente PostgreSQL base
├── cacheMemoria.ts # Cache em memória (Map com TTL)
├── aleatorio.ts # Utilitários de aleatoriedade
├── consulta.ts # Helpers de consulta SQL
├── instalarAmbiente.ts # Setup de ambiente (dev/prod)
├── graficosPilao.ts # Tipos para gráficos do PILÃO
├── ecosistema/ # Tipos do ecossistema de módulos
└── testes/ # Testes unitários (Vitest)
📐 Convenções de Código
TypeScript
- Strict mode SEMPRE ligado (
"strict": true) - Sem
anyexplícito — use tipos genéricos ouunknown - Sem
!(non-null assertion) — trate onull/undefinedexplicitamente - Arrays: usar
T[]em vez deArray<T>(shorthand) - Imports ordenados automaticamente pelo Biome
- Enums sempre com inicializadores explícitos
- Parâmetros não podem ser reatribuídos
Nomenclatura
// Tipos e interfaces: PascalCase
type TipoUsuario = { ... }
interface IRepositorio { ... }
// Constantes: camelCase (sem SCREAMING_SNAKE_CASE, exceto enums legados)
const configuracaoBase = { ... }
// Funções: camelCase, verbos
const calcularTotal = (itens: Item[]) => { ... }
const buscarUsuarioPorId = async (id: UUID) => { ... }
// Arquivos: camelCase para utilitários, PascalCase para componentes Vue
// ✅ tipoFiltro.ts, variaveisComuns.ts
// ✅ MeuComponente.vue, BotaoAcao.vue
Vue 3 (Composition API)
<script setup lang="ts">
// Sempre usar <script setup lang="ts">
// Macros globais disponíveis (sem import): defineProps, defineEmits,
// defineExpose, withDefaults, defineModel, defineOptions, defineSlots
const props = defineProps<{
titulo: string
itens: Item[]
}>()
const emit = defineEmits<{
selecionar: [item: Item]
fechar: []
}>()
</script>
- Sem Vue Options API — sempre Composition API
- Props não devem ser desestruturadas (quebra reatividade Vue 3)
v-forsempre com:key— use o ID do item, nunca o índice!v-ifev-fornunca no mesmo elemento — use<template v-for>- Atributos em multiline quando há mais de 2 props
TSX (componentes em .tsx)
// Componente funcional Vue em TSX
import { defineComponent, ref } from "vue"
export const MeuComponente = defineComponent({
props: {
titulo: { type: String, required: true },
},
setup(props) {
const contador = ref(0)
return () => (
<div class="meu-componente">
<h1>{props.titulo}</h1>
<button onClick={() => contador.value++}>{contador.value}</button>
</div>
)
},
})
🔧 Biome — Regras de Lint Importantes
Erros (bloqueiam o build)
| Regra | Descrição |
|---|---|
noUnusedVariables |
Variáveis definidas e não usadas |
noUnusedImports |
Imports não utilizados |
noVoidTypeReturn |
Função void retornando valor |
noVueDataObjectDeclaration |
Vue 2 data: {} — usar função |
noVueDuplicateKeys |
Chaves duplicadas em objetos Vue |
noVueSetupPropsReactivityLoss |
Desestruturar props em setup() |
noVueVIfWithVFor |
v-if + v-for no mesmo elemento |
useVueVForKey |
v-for sem :key |
useVueValidTemplateRoot |
Template sem raiz única (Vue 2) |
Warnings (code smells — corrija quando possível)
| Regra | Descrição |
|---|---|
useArrowFunction |
Sempre use arrow function — function é erro |
noNonNullAssertion |
Evite ! — trate o null |
noDelete |
delete obj.prop é lento |
noEmptyBlockStatements |
Blocos {} vazios |
noArrayIndexKey |
:key com índice do array |
noDangerouslySetInnerHtml |
innerHTML perigoso |
noExcessiveCognitiveComplexity |
Função muito complexa (max: 20) |
📦 Como Outros Projetos Consomem Este Pacote
// biome.json do subprojeto (ex: PILAO-FRONT)
{
"$schema": "./node_modules/@biomejs/biome/configuration_schema.json",
"extends": ["./node_modules/p-comuns/Documentos/biome.json"],
"files": {
"includes": ["src/**/*.{js,ts,jsx,tsx,vue}"]
}
}
// .vscode/settings.json do subprojeto
{
"editor.defaultFormatter": "biomejs.biome",
"editor.formatOnSave": true,
"editor.codeActionsOnSave": {
"source.organizeImports.biome": "always",
"source.fixAll.biome": "always"
},
"[vue]": { "editor.defaultFormatter": "biomejs.biome" },
"[typescript]": { "editor.defaultFormatter": "biomejs.biome" },
"[typescriptreact]": { "editor.defaultFormatter": "biomejs.biome" },
"editor.rulers": [100],
"files.eol": "\n"
}
🚀 Scripts
pnpm biome # Formata + lint com auto-fix
pnpm check # biome + tsc --noEmit (sem emitir arquivos)
pnpm build # Bump de versão + biome + tsup + pack
pnpm teste # Vitest (testes unitários)
⚠️ O que NÃO fazer
- ❌ Não use
eslint— o projeto usa Biome - ❌ Não use
prettier— o projeto usa Biome - ❌ Não use
functionnomeada — sempre arrow function (const fn = () => {}) - ❌ Não use Vue Options API — sempre Composition API
- ❌ Não desestrure
propsdiretamente (quebra reatividade) - ❌ Não use
any— useunknown+ type narrowing - ❌ Não use índice como
:keynov-for - ❌ Não quebre linhas com mais de 100 caracteres
- ❌ Não use ponto-e-vírgula no final (Biome removerá)