.
This commit is contained in:
parent
f5abcec365
commit
e7adba8fd8
84 changed files with 4222 additions and 2182 deletions
|
|
@ -6,7 +6,7 @@ description: Princípios morais e operacionais que orientam o comportamento de a
|
|||
version: "1.0"
|
||||
scope: global
|
||||
priority: alta
|
||||
updatedAt: "2026-06-01"
|
||||
updatedAt: "2026-08-11"
|
||||
---
|
||||
|
||||
# Carta de Princípios do Agente de IA da Azteca
|
||||
|
|
|
|||
|
|
@ -1,154 +0,0 @@
|
|||
---
|
||||
type: rule
|
||||
name: consultar-banco-query-ia
|
||||
description: Define como agentes devem consultar o banco de dados via rota dedicada /query-ia — proibindo acesso direto ao banco fora deste protocolo
|
||||
scope: global
|
||||
trigger: context_match
|
||||
priority: alta
|
||||
updatedAt: "2026-07-01"
|
||||
---
|
||||
|
||||
# Regra: Consultar Banco de Dados via `/query-ia`
|
||||
|
||||
## Contexto
|
||||
|
||||
Quando um agente precisa inspecionar dados reais do banco de dados — para diagnóstico, auditoria, validação de registros ou investigação de bugs — existe uma rota dedicada e segura para isso no backend do projeto.
|
||||
|
||||
Essa rota é exclusiva para desenvolvimento e **nunca deve ser usada em produção**. Ela bloqueia automaticamente comandos destrutivos.
|
||||
|
||||
## Rota
|
||||
|
||||
```
|
||||
GET http://127.0.0.1:<porta-back>/query-ia → retorna documentação da rota (texto plano)
|
||||
POST http://127.0.0.1:<porta-back>/query-ia → executa consulta SQL e retorna JSON
|
||||
```
|
||||
|
||||
> **`<porta-back>` é subjetiva** — cada módulo do ecossistema usa uma porta diferente. Antes de usar a rota, descobrir a porta correta do projeto atual:
|
||||
> - Verificar `package.json` do `*-back` (campo `scripts.dev` ou `scripts.start`)
|
||||
> - Ou verificar a variável `PORT` no `.env` do módulo
|
||||
|
||||
## Como usar
|
||||
|
||||
### Descobrir a porta e consultar a documentação
|
||||
|
||||
```bash
|
||||
# Verificar a porta no package.json do módulo back
|
||||
cat package.json | jq '.scripts.dev'
|
||||
|
||||
# Consultar a documentação da rota (substitua <porta-back> pela porta real)
|
||||
curl http://127.0.0.1:<porta-back>/query-ia
|
||||
```
|
||||
|
||||
### Executar uma consulta SQL
|
||||
|
||||
```bash
|
||||
curl -s -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-H 'Content-Type: application/json' \
|
||||
-d '{
|
||||
"sql": "SELECT * FROM empresas LIMIT 10",
|
||||
"parametros": []
|
||||
}' | jq .
|
||||
```
|
||||
|
||||
### Consulta com parâmetros (binding seguro)
|
||||
|
||||
```bash
|
||||
curl -s -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-H 'Content-Type: application/json' \
|
||||
-d '{
|
||||
"sql": "SELECT * FROM avaliacoes WHERE empresa_id = ? AND status = ?",
|
||||
"parametros": ["uuid-da-empresa", "aprovado"]
|
||||
}' | jq .
|
||||
```
|
||||
|
||||
## Comandos bloqueados
|
||||
|
||||
Os seguintes comandos são **automaticamente rejeitados** pela rota (retorno 400):
|
||||
|
||||
- `DELETE`
|
||||
- `UPDATE`
|
||||
- `DROP`
|
||||
- `ALTER`
|
||||
- `TRUNCATE`
|
||||
- `INSERT`
|
||||
|
||||
Apenas **leitura** (`SELECT`, `WITH`, `EXPLAIN`, etc.) é permitida.
|
||||
|
||||
## Retorno
|
||||
|
||||
```json
|
||||
{
|
||||
"rows": [...],
|
||||
"rowCount": 42
|
||||
}
|
||||
```
|
||||
|
||||
Em caso de erro SQL:
|
||||
|
||||
```json
|
||||
{
|
||||
"erro": "mensagem de erro",
|
||||
"stack": "stack trace (apenas em desenvolvimento)"
|
||||
}
|
||||
```
|
||||
|
||||
## Regra
|
||||
|
||||
O agente **DEVE** usar esta rota sempre que precisar de dados reais do banco — diagnóstico, contagem de registros, verificação de estado, auditoria de dados.
|
||||
|
||||
O agente **NUNCA** deve:
|
||||
|
||||
- Tentar acessar o banco diretamente via código (modificar arquivos para adicionar logs de DB)
|
||||
- Inventar dados ou assumir estado sem verificar
|
||||
- Usar esta rota para comandos de escrita — use as APIs REST do módulo para isso
|
||||
|
||||
## Exemplos
|
||||
|
||||
### ✅ Correto — inspecionar registros via query-ia
|
||||
|
||||
```bash
|
||||
curl -s -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-d '{"sql": "SELECT codigo, nome, status FROM empresas ORDER BY criado_em DESC LIMIT 20"}' \
|
||||
-H 'Content-Type: application/json' | jq '.rows'
|
||||
```
|
||||
|
||||
### ✅ Correto — verificar schemas PostgreSQL disponíveis
|
||||
|
||||
```bash
|
||||
curl -s -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-d '{"sql": "SELECT schema_name FROM information_schema.schemata ORDER BY schema_name"}' \
|
||||
-H 'Content-Type: application/json' | jq '.rows'
|
||||
```
|
||||
|
||||
### ✅ Correto — contar registros por inquilino
|
||||
|
||||
```bash
|
||||
curl -s -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-d '{"sql": "SELECT inquilino, COUNT(*) as total FROM empresas GROUP BY inquilino"}' \
|
||||
-H 'Content-Type: application/json' | jq '.rows'
|
||||
```
|
||||
|
||||
### ❌ Errado — tentar escrever via query-ia
|
||||
|
||||
```bash
|
||||
# Será bloqueado com status 400
|
||||
curl -X POST http://127.0.0.1:<porta-back>/query-ia \
|
||||
-d '{"sql": "UPDATE empresas SET status = ?", "parametros": ["ativo"]}'`
|
||||
```
|
||||
|
||||
### ❌ Errado — modificar código para adicionar log de banco
|
||||
|
||||
```typescript
|
||||
// NÃO fazer isso para "ver os dados" — usar a rota query-ia
|
||||
const debug = await dbKnex('empresas').select('*').limit(10)
|
||||
console.log(debug)
|
||||
```
|
||||
|
||||
## Impacto
|
||||
|
||||
Sem esta regra, agentes podem modificar código de produção apenas para inspecionar dados, ou assumir estados do banco sem verificação — gerando diagnósticos incorretos e alterações desnecessárias.
|
||||
|
||||
## Referências
|
||||
|
||||
- Implementação de referência: `qualifica-back/src/utilitarios-IA/query-ia.ts`
|
||||
- Rule: `global/rules/autonomia-agente` (ações autônomas sem aprovação)
|
||||
53
global/rules/copywriting-landing.md
Normal file
53
global/rules/copywriting-landing.md
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
---
|
||||
type: rule
|
||||
name: copywriting-landing
|
||||
description: Diretrizes de Copywriting, Design Visual, Formulários, SEO Técnico e CRO para Landing Pages de Alta Conversão
|
||||
scope: [landing-pages, CRO, copywriting, SEO]
|
||||
trigger: model_decision
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Diretrizes de Copywriting, Design e CRO para Landing Pages (@land)
|
||||
|
||||
## Copywriting de Alta Conversão
|
||||
|
||||
### Framework 4C
|
||||
1. **Clarity (Clareza):** Entendimento da oferta nos primeiros 5 segundos.
|
||||
2. **Comprehension (Compreensão):** Explicação clara do "como" a solução atua.
|
||||
3. **Credibility (Credibilidade):** Números, depoimentos e logos reais.
|
||||
4. **Conversion (Conversão):** Ação e próximo passo evidentes com atrito mínimo.
|
||||
|
||||
### Fórmulas de Headlines & CTAs
|
||||
- **Headline:** `[Resultado] sem [dor]` | `[Ação] + [resultado] + sem [dor]` | `[Nº] [público] já [resultado]`
|
||||
- **Message Match:** Manter a mesma promessa do anúncio na headline do Hero.
|
||||
- **CTA:** `Solicitar Demonstração Gratuita` | `Ver como funciona` | `Falar com especialista`
|
||||
|
||||
---
|
||||
|
||||
## Design Visual & Psicologia (Regra 60-30-10)
|
||||
|
||||
- **60% Dominante:** Backgrounds e áreas principais.
|
||||
- **30% Secundária:** Seções, cards e destaques.
|
||||
- **10% Acento:** CTAs e alertas (máximo contraste).
|
||||
- **Tipografia:** H1 48-56px Bold | Body 16-18px Regular (Line-height 1.6x).
|
||||
- **Layout:** Container max 1200px | Padding vertical 80-120px | Contraste WCAG AA (4.5:1).
|
||||
- **Mídia:** Screenshots reais do produto (NUNCA stock photos genéricas).
|
||||
|
||||
---
|
||||
|
||||
## Formulários Otimizados (Máximo 4 Campos)
|
||||
|
||||
1. Nome (texto)
|
||||
2. E-mail corporativo (email)
|
||||
3. Telefone/WhatsApp (tel)
|
||||
4. Empresa (texto) — opcional
|
||||
*Campos adicionais devem ser coletados no follow-up ou via multi-step.*
|
||||
|
||||
---
|
||||
|
||||
## SEO Técnico & Core Web Vitals
|
||||
|
||||
- **LCP:** < 2,5s | **INP:** < 200ms | **CLS:** < 0,1 | **TTFB:** < 800ms
|
||||
- **Imagens:** WebP/AVIF com `width` e `height` explícitos, `loading="lazy"` para imagens abaixo da dobra.
|
||||
- **Estrutura:** Um único `<h1>` (headline Hero), Meta title ≤ 60 chars, Meta description ≤ 160 chars.
|
||||
- **Schema.org:** Markup de `Organization`, `SoftwareApplication` e `FAQPage`.
|
||||
|
|
@ -3,9 +3,9 @@ type: rule
|
|||
name: css-global-betha
|
||||
description: Define o padrão de CSS global com variáveis --bth-* para todos os frontends do ecossistema GOV (QUIPO-FRONT, QUIPO-PORTAL3, AUTENTICACAO-FRONT, QUIPO-CONSOLE)
|
||||
scope: global
|
||||
trigger: context_match
|
||||
trigger: model_decision
|
||||
priority: alta
|
||||
updatedAt: "2026-07-02"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: CSS Global Betha — Variáveis `--bth-*`
|
||||
|
|
|
|||
70
global/rules/design-patterns-pragmatico.md
Normal file
70
global/rules/design-patterns-pragmatico.md
Normal file
|
|
@ -0,0 +1,70 @@
|
|||
---
|
||||
type: rule
|
||||
name: design-patterns-pragmatico
|
||||
description: Aplicar Design Patterns GoF apenas quando há problema concreto que o justifique
|
||||
scope: local
|
||||
trigger: model_decision
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Design Patterns Pragmático
|
||||
|
||||
## Contexto
|
||||
|
||||
Os 22 Design Patterns GoF são soluções comprovadas para problemas recorrentes. Porém, aplicar um padrão sem problema concreto cria complexidade gratuita — o code smell "Generalidade Especulativa".
|
||||
|
||||
## Regra
|
||||
|
||||
**Antes de introduzir qualquer Design Pattern:**
|
||||
|
||||
1. Identificar o **problema concreto** que existe agora (não no futuro hipotético)
|
||||
2. Nomear o **code smell** que o padrão resolve
|
||||
3. Avaliar se a **complexidade do padrão** é justificada pelo tamanho do problema
|
||||
4. Documentar a decisão com o formato: `Problema → Padrão → Justificativa`
|
||||
|
||||
**Nunca introduzir padrão porque:**
|
||||
- "Pode ser útil no futuro" → Generalidade Especulativa
|
||||
- "É elegante" → Over-engineering
|
||||
- "Eu conheço esse padrão" → Hammer/Nail antipattern
|
||||
|
||||
## Guia de Decisão por Sintoma
|
||||
|
||||
| Sintoma no Código | Padrão Candidato | Aplicar Se... |
|
||||
|-------------------|------------------|---------------|
|
||||
| `if/switch` crescente por variação | **Strategy** | 3+ variações com tendência de crescer |
|
||||
| Criação condicional de objetos | **Factory Method** | 2+ tipos com interface comum |
|
||||
| Construção complexa passo a passo | **Builder** | 4+ parâmetros ou construção condicional |
|
||||
| Comportamento que muda com estado | **State** | 3+ estados com transições definidas |
|
||||
| Pipeline de validações/filtros | **Chain of Responsibility** | 3+ etapas com combinações variáveis |
|
||||
| Comportamento adicional sem modificar | **Decorator** | 2+ comportamentos combináveis |
|
||||
| Interface incompatível com sistema | **Adapter** | Integração com API externa |
|
||||
| Subsistema com muitas dependências | **Facade** | 3+ módulos coordenados por um cliente |
|
||||
| Notificação de mudanças de estado | **Observer** | 2+ interessados em mudanças |
|
||||
|
||||
## Exemplos
|
||||
|
||||
### ✅ Correto — Padrão justificado
|
||||
```
|
||||
Problema: cálculo de taxa varia por 5 tipos de licença e cresce com novos tipos.
|
||||
Code smell: switch crescente (violação Open/Closed).
|
||||
Padrão: Strategy via dispatch table.
|
||||
Justificativa: elimina switch, cada novo tipo é arquivo separado.
|
||||
```
|
||||
|
||||
### ❌ Incorreto — Padrão especulativo
|
||||
```
|
||||
Problema: nenhum. Temos apenas 1 tipo de notificação.
|
||||
Padrão: Observer com EventEmitter customizado.
|
||||
Motivo: "talvez no futuro tenha mais tipos".
|
||||
Resultado: 4 arquivos novos para resolver 0 problemas.
|
||||
```
|
||||
|
||||
## Impacto
|
||||
|
||||
Padrões aplicados sem critério geram código mais complexo sem benefício proporcional, violando o princípio YAGNI (You Aren't Gonna Need It).
|
||||
|
||||
## Referências
|
||||
|
||||
- Alexander Shvets — "Mergulho nos Padrões de Projeto" (Refactoring.Guru)
|
||||
- GoF — "Design Patterns: Elements of Reusable Object-Oriented Software"
|
||||
- Persona: `agents/refatorar/persona`
|
||||
156
global/rules/drive-entidades-internas.md
Normal file
156
global/rules/drive-entidades-internas.md
Normal file
|
|
@ -0,0 +1,156 @@
|
|||
---
|
||||
type: rule
|
||||
name: drive-entidades-internas
|
||||
description: Consultar entidades do e-licencie (empreendedor, empreendimento, usuário) via eLicencieDrive com token interno
|
||||
scope: local
|
||||
trigger: model_decision
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Consultar Entidades do e-licencie via Drive Interno
|
||||
|
||||
## Contexto
|
||||
|
||||
Dentro de `sigma-back/src/INFO/` e `sigma-back/src/_FILAS/`, quando um gerador de info
|
||||
ou um worker de fila precisa dos dados de **empreendedor**, **empreendimento** ou
|
||||
**usuário**, esses dados **não existem localmente no banco do SIGMA** — eles vivem no
|
||||
e-licencie. A consulta deve ser feita via `eLicencieDrive` com token interno,
|
||||
nunca retornando campos em branco (`nome: ""`, `documento: ""`).
|
||||
|
||||
## Regra
|
||||
|
||||
### 1. Instanciar o drive com token interno
|
||||
|
||||
Sempre usar `montarTokenInterno({ inquilino })` para autenticar o drive.
|
||||
O `inquilino` já está disponível no contexto do gerador (`tipoGeradorInfo`) e
|
||||
no worker de fila (extraído do schema).
|
||||
|
||||
```ts
|
||||
import { eLicencieDrive, montarTokenInterno } from "../plugins/e-licencie-drive"
|
||||
|
||||
const drive = eLicencieDrive({ token: montarTokenInterno({ inquilino }) })
|
||||
```
|
||||
|
||||
### 2. Preferir os helpers de `cacheEntidadesDrive`
|
||||
|
||||
Para buscas pontuais por código, usar os helpers prontos de
|
||||
`sigma-back/src/e-licencie-drive/cacheEntidadesDrive.ts`:
|
||||
|
||||
```ts
|
||||
import {
|
||||
obterEmpreendedorPorCodigo,
|
||||
obterEmpreendimentoPorCodigo,
|
||||
obterUsuarioPorCodigo,
|
||||
} from "../e-licencie-drive/cacheEntidadesDrive"
|
||||
|
||||
// dentro do gerador de info (já tem inquilino no contexto):
|
||||
const empreendedor = await obterEmpreendedorPorCodigo(
|
||||
objeto.codigo_empreendedor,
|
||||
montarTokenInterno({ inquilino }),
|
||||
)
|
||||
```
|
||||
|
||||
### 3. Nunca retornar campos em branco
|
||||
|
||||
É **proibido** retornar `nome: ""` ou `documento: ""` quando esses dados
|
||||
podem ser obtidos pelo drive.
|
||||
|
||||
```ts
|
||||
// ❌ ERRADO — dado em branco não tem utilidade para busca ou exibição
|
||||
return respostaComuns.valor({
|
||||
codigo: objeto.codigo_empreendedor,
|
||||
nome: "",
|
||||
documento: "",
|
||||
})
|
||||
|
||||
// ✅ CORRETO — consultar e retornar dados reais
|
||||
const emp = await obterEmpreendedorPorCodigo(
|
||||
objeto.codigo_empreendedor,
|
||||
montarTokenInterno({ inquilino }),
|
||||
)
|
||||
return respostaComuns.valor({
|
||||
codigo: objeto.codigo_empreendedor,
|
||||
nome: emp?.nome ?? "",
|
||||
documento: emp?.documento ?? "",
|
||||
})
|
||||
```
|
||||
|
||||
### 4. O `inquilino` já está disponível — não inventar
|
||||
|
||||
Nos geradores de info (`tipoGeradorInfo`), o parâmetro `{ objeto, schema, inquilino }`
|
||||
já inclui `inquilino`. Na fila `_recalcular_todos_infos`, o `inquilino` é extraído
|
||||
do schema via `decodeURIComponent(parts[2])`. Não é necessário buscá-lo de outra forma.
|
||||
|
||||
### 5. Tratar falha do drive com fallback
|
||||
|
||||
Se o drive retornar erro, registrar no log e retornar campos vazios — **nunca lançar**
|
||||
exceção que interrompa o recálculo global de infos.
|
||||
|
||||
```ts
|
||||
const emp = await obterEmpreendedorPorCodigo(
|
||||
objeto.codigo_empreendedor,
|
||||
montarTokenInterno({ inquilino }),
|
||||
)
|
||||
if (!emp) {
|
||||
console.warn("[info] Empreendedor não encontrado no drive:", objeto.codigo_empreendedor)
|
||||
}
|
||||
return respostaComuns.valor({
|
||||
codigo: objeto.codigo_empreendedor,
|
||||
nome: emp?.nome ?? "",
|
||||
documento: emp?.documento ?? "",
|
||||
})
|
||||
```
|
||||
|
||||
## Exemplos
|
||||
|
||||
### ✅ Correto — `_registros.ts` consultando drive
|
||||
|
||||
```ts
|
||||
empreendedor: async ({ objeto, inquilino }) => {
|
||||
const emp = await obterEmpreendedorPorCodigo(
|
||||
objeto.codigo_empreendedor,
|
||||
montarTokenInterno({ inquilino }),
|
||||
)
|
||||
return respostaComuns.valor({
|
||||
codigo: objeto.codigo_empreendedor,
|
||||
nome: emp?.nome ?? "",
|
||||
documento: emp?.documento ?? "",
|
||||
})
|
||||
},
|
||||
```
|
||||
|
||||
### ❌ Incorreto — retornar em branco sem consultar
|
||||
|
||||
```ts
|
||||
empreendedor: async ({ objeto }) => {
|
||||
return respostaComuns.valor({
|
||||
codigo: objeto.codigo_empreendedor,
|
||||
nome: "", // ← proibido quando drive está disponível
|
||||
documento: "", // ← proibido quando drive está disponível
|
||||
})
|
||||
},
|
||||
```
|
||||
|
||||
### ✅ Correto — worker de fila com drive
|
||||
|
||||
```ts
|
||||
// inquilino já extraído do schema
|
||||
const drive = eLicencieDrive({ token: montarTokenInterno({ inquilino }) })
|
||||
const resultado = await drive.listarEmpreendedores()
|
||||
```
|
||||
|
||||
## Arquivos de referência
|
||||
|
||||
| Arquivo | Papel |
|
||||
|---|---|
|
||||
| `sigma-back/src/plugins/e-licencie-drive.ts` | Ponto único de importação do drive + `montarTokenInterno` |
|
||||
| `sigma-back/src/e-licencie-drive/cacheEntidadesDrive.ts` | Helpers: `obterEmpreendedorPorCodigo`, `obterEmpreendimentoPorCodigo`, `obterUsuarioPorCodigo` |
|
||||
| `sigma-back/src/INFO/tipagem.ts` | Define `tipoGeradorInfo<T>` com `{ objeto, schema, inquilino }` |
|
||||
| `sigma-back/src/INFO/index.ts` | `gravarInfo` — repassa `inquilino` para cada gerador |
|
||||
|
||||
## Impacto
|
||||
|
||||
Sem esta regra:
|
||||
- Campos `nome` e `documento` ficam em branco no JSONB `info`, quebrando buscas textuais e exibição no frontend
|
||||
- O drive é instanciado sem uso (código morto)
|
||||
- Geradores novos podem replicar o padrão incorreto sem saber que o drive está disponível
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
---
|
||||
type: rule
|
||||
name: escrita-natural
|
||||
trigger: context_match
|
||||
trigger: model_decision
|
||||
description: Garantir escrita natural, fluida e humana em textos comerciais e de comunicação, evitando linguagem robótica ou excessivamente genérica.
|
||||
scope: global
|
||||
updatedAt: "2026-06-01"
|
||||
updatedAt: "2026-09-28"
|
||||
ativacao: >
|
||||
Aplicar quando o agente estiver produzindo textos comerciais, de marketing,
|
||||
orçamentos, propostas, reels ou qualquer comunicação voltada ao público externo.
|
||||
|
|
|
|||
|
|
@ -3,8 +3,8 @@ type: rule
|
|||
name: estilos-design-system
|
||||
description: Define os dois design systems do ecossistema e-licencie — Floreta (iniciativa privada) e Betha (governo) — e quando usar cada um
|
||||
scope: global
|
||||
trigger: always
|
||||
updatedAt: "2026-07-02"
|
||||
trigger: always_on
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Estilos e Design Systems do Ecossistema
|
||||
|
|
|
|||
85
global/rules/estrutura-vue.md
Normal file
85
global/rules/estrutura-vue.md
Normal file
|
|
@ -0,0 +1,85 @@
|
|||
---
|
||||
type: rule
|
||||
name: estrutura-vue
|
||||
description: Padrões obrigatórios de estrutura para componentes Vue 3 (defineComponent, setup, CSS, dispatch)
|
||||
scope: local
|
||||
trigger: glob
|
||||
globs: "**/*.vue"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Estrutura de Componentes Vue
|
||||
|
||||
## 1. `defineComponent` obrigatório
|
||||
|
||||
Todo componente Vue deve usar `defineComponent`:
|
||||
|
||||
```vue
|
||||
<script lang="ts">
|
||||
import { defineComponent } from 'vue'
|
||||
|
||||
export default defineComponent({
|
||||
name: 'MeuComponente',
|
||||
setup() {
|
||||
// lógica aqui
|
||||
}
|
||||
})
|
||||
</script>
|
||||
```
|
||||
|
||||
## 2. `setup()` não pode ser externo
|
||||
|
||||
O `setup()` deve estar sempre dentro do `.vue`. Nunca delegar para arquivo externo.
|
||||
|
||||
```ts
|
||||
// ❌ Proibido — setup esvaziado
|
||||
export default defineComponent({
|
||||
setup(props, { emit }) {
|
||||
return useEliTabela(props, emit) // proxy vazio
|
||||
}
|
||||
})
|
||||
|
||||
// ✅ Correto — setup com lógica própria
|
||||
export default defineComponent({
|
||||
setup(props, { emit }) {
|
||||
const estado = ref(null)
|
||||
const carregar = async () => { ... }
|
||||
return { estado, carregar }
|
||||
}
|
||||
})
|
||||
```
|
||||
|
||||
> Composables `use*.ts` podem encapsular lógica reutilizável pontual, mas nunca substituir o `setup()`. Se ultrapassar 250 linhas → extrair subcomponentes, CSS ou Dispatch Table.
|
||||
|
||||
## 3. CSS co-localizado
|
||||
|
||||
Separação de estilos em arquivo externo quando o CSS contribui para o total de linhas:
|
||||
|
||||
```
|
||||
MeuComponente.vue
|
||||
MeuComponente.css
|
||||
```
|
||||
|
||||
Importar via `import './MeuComponente.css'` ou `<style src="./MeuComponente.css" />`.
|
||||
|
||||
## 4. Dispatch Table
|
||||
|
||||
Uso de mapa de funções para eliminar `if/else` ou `switch` longos:
|
||||
|
||||
```ts
|
||||
// handlers.ts
|
||||
export const acaoHandlers: Record<string, () => void> = {
|
||||
salvar: () => { ... },
|
||||
cancelar: () => { ... },
|
||||
excluir: () => { ... },
|
||||
}
|
||||
```
|
||||
|
||||
## Impacto
|
||||
|
||||
Sem estes padrões, componentes perdem inferência de tipos, lógica fica inauditável em composables externos, e CSS cresce inline sem controle.
|
||||
|
||||
## Referências
|
||||
|
||||
- Rule: `global/rules/limite-linhas`
|
||||
- Rule: `global/rules/typescript-sem-any`
|
||||
|
|
@ -3,13 +3,9 @@ type: rule
|
|||
name: jsdoc-padrao
|
||||
description: Padrões de documentação em código-fonte (comentários claros e coerentes quanto à aplicação, JSDoc, casts e TODOs).
|
||||
scope: global
|
||||
trigger: file_match
|
||||
globs:
|
||||
- "**/*.ts"
|
||||
- "**/*.tsx"
|
||||
- "**/*.vue"
|
||||
- "**/*.js"
|
||||
updatedAt: "2026-09-01"
|
||||
trigger: glob
|
||||
globs: "**/*.ts, **/*.tsx, **/*.vue, **/*.js"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Documentação e Comentários no Código-Fonte
|
||||
|
|
|
|||
|
|
@ -3,13 +3,9 @@ type: rule
|
|||
name: limite-linhas
|
||||
description: Nenhum arquivo de código pode ultrapassar 250 linhas
|
||||
scope: global
|
||||
trigger: file_match
|
||||
globs:
|
||||
- "**/*.ts"
|
||||
- "**/*.tsx"
|
||||
- "**/*.vue"
|
||||
- "**/*.css"
|
||||
updatedAt: "2026-06-01"
|
||||
trigger: glob
|
||||
globs: "**/*.ts, **/*.tsx, **/*.vue, **/*.css"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Limite de 250 Linhas por Arquivo
|
||||
|
|
|
|||
|
|
@ -3,12 +3,9 @@ type: rule
|
|||
name: mensagens-usuario
|
||||
description: Toda mensagem visível ao usuário final deve ser escrita em linguagem do domínio, sem termos técnicos de TI
|
||||
scope: global
|
||||
trigger: file_match
|
||||
globs:
|
||||
- "**/*.vue"
|
||||
- "**/*.ts"
|
||||
- "**/*.tsx"
|
||||
updatedAt: "2026-06-01"
|
||||
trigger: glob
|
||||
globs: "**/*.vue, **/*.ts, **/*.tsx"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Mensagens Orientadas ao Domínio
|
||||
|
|
|
|||
|
|
@ -3,9 +3,9 @@ type: rule
|
|||
name: modal-dialog-padrao-betha
|
||||
description: Define a estrutura obrigatória de modais e dialogs MUI no padrão Betha — header escuro, body branco, footer cinza — para os frontends React do ecossistema GOV
|
||||
scope: global
|
||||
trigger: context_match
|
||||
trigger: model_decision
|
||||
priority: alta
|
||||
updatedAt: "2026-07-02"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Padrão Modal/Dialog MUI — Estrutura Betha
|
||||
|
|
|
|||
56
global/rules/refatoracao-segura.md
Normal file
56
global/rules/refatoracao-segura.md
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
---
|
||||
type: rule
|
||||
name: refatoracao-segura
|
||||
description: Toda refatoração deve preservar comportamento e ter cobertura de testes
|
||||
scope: local
|
||||
trigger: always_on
|
||||
updatedAt: "2026-06-19"
|
||||
---
|
||||
|
||||
# Regra: Refatoração Segura
|
||||
|
||||
## Contexto
|
||||
|
||||
Refatoração é a melhoria da estrutura interna do código **sem alterar seu comportamento externo**. Sem essa garantia, refatoração vira regressão.
|
||||
|
||||
## Regra
|
||||
|
||||
Antes de executar qualquer refatoração, verificar:
|
||||
|
||||
1. **Testes existem** — o comportamento que será afetado tem cobertura
|
||||
2. **Testes passam** — o estado antes da mudança é verde
|
||||
3. **Passos pequenos** — cada mudança deve ser verificável isoladamente
|
||||
4. **Sem surpresas** — nenhuma funcionalidade nova introduzida junto com refatoração
|
||||
|
||||
Se não há testes cobrindo o trecho:
|
||||
- **PARAR** a refatoração
|
||||
- Solicitar ao `@testes` a criação de testes de cobertura
|
||||
- Só prosseguir após testes existirem e passarem
|
||||
|
||||
## Exemplos
|
||||
|
||||
### ✅ Correto
|
||||
```
|
||||
1. Verificar testes existentes para `calcularLicenca()`
|
||||
2. Executar testes → todos passam
|
||||
3. Extrair cálculo de multa para `calcularMulta()`
|
||||
4. Executar testes → todos passam
|
||||
5. Commit: "refactor: extrair calcularMulta de calcularLicenca"
|
||||
```
|
||||
|
||||
### ❌ Incorreto
|
||||
```
|
||||
1. Refatorar `calcularLicenca()` inteiro
|
||||
2. Adicionar nova regra de desconto (feature!)
|
||||
3. Descobrir que não tinha testes
|
||||
4. Commit: "refactor: melhorar cálculos" ← mentira, é feature + refatoração
|
||||
```
|
||||
|
||||
## Impacto
|
||||
|
||||
Sem esta regra, refatorações introduzem regressões silenciosas que só são descobertas em produção.
|
||||
|
||||
## Referências
|
||||
|
||||
- Martin Fowler — "Refactoring: Improving the Design of Existing Code"
|
||||
- Persona: `agents/refatorar/persona`
|
||||
88
global/rules/solid-compliance.md
Normal file
88
global/rules/solid-compliance.md
Normal file
|
|
@ -0,0 +1,88 @@
|
|||
---
|
||||
type: rule
|
||||
name: solid-compliance
|
||||
description: Todo código deve aderir aos 5 princípios SOLID do Refactoring.Guru
|
||||
scope: local
|
||||
trigger: model_decision
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: Conformidade SOLID
|
||||
|
||||
## Contexto
|
||||
|
||||
Os princípios SOLID são o alicerce de software manutenível. Violações geram acoplamento, rigidez e fragilidade que crescem exponencialmente com o tempo.
|
||||
|
||||
## Regra
|
||||
|
||||
Ao analisar ou modificar código, verificar conformidade com cada princípio:
|
||||
|
||||
### S — Responsabilidade Única
|
||||
|
||||
- Cada arquivo tem uma única razão para mudar
|
||||
- Funções fazem uma única coisa
|
||||
- Composables encapsulam um único domínio de estado
|
||||
|
||||
**Indicador de violação:** arquivo que precisa mudar quando regras de negócio **E** regras de apresentação mudam.
|
||||
|
||||
### O — Aberto/Fechado
|
||||
|
||||
- Novas funcionalidades adicionadas por extensão (novos arquivos), não por edição de existentes
|
||||
- Usar dispatch tables, strategy pattern ou plugins
|
||||
|
||||
**Indicador de violação:** `if/else` ou `switch` que cresce a cada nova variação.
|
||||
|
||||
### L — Substituição de Liskov
|
||||
|
||||
- Subtipos podem ser usados onde o tipo base é esperado
|
||||
- Funções que aceitam um tipo base funcionam com qualquer subtipo
|
||||
|
||||
**Indicador de violação:** `instanceof` ou type guards que verificam subtipos para mudar comportamento.
|
||||
|
||||
### I — Segregação de Interface
|
||||
|
||||
- Tipos/interfaces contêm apenas os membros que seus consumidores usam
|
||||
- Nenhum módulo é forçado a depender de métodos que não utiliza
|
||||
|
||||
**Indicador de violação:** tipo com campos opcionais demais (`?`) que na prática são obrigatórios em alguns contextos.
|
||||
|
||||
### D — Inversão de Dependência
|
||||
|
||||
- Módulos de lógica de negócio não importam de módulos de infraestrutura diretamente
|
||||
- Dependência flui através de abstrações (interfaces, tipos, schemas Zod)
|
||||
|
||||
**Indicador de violação:** serviço de negócio importando driver de banco ou cliente HTTP diretamente.
|
||||
|
||||
## Exemplos
|
||||
|
||||
### ✅ Correto — Princípio O (Aberto/Fechado)
|
||||
```ts
|
||||
// dispatch table: extensível sem editar código existente
|
||||
const calculadores: Record<TipoLicenca, CalculadorFn> = {
|
||||
ambiental: calcularAmbiental,
|
||||
sanitaria: calcularSanitaria,
|
||||
// nova licença? adicionar aqui sem tocar nas funções existentes
|
||||
}
|
||||
```
|
||||
|
||||
### ❌ Incorreto — Violação do Princípio S (Responsabilidade Única)
|
||||
```ts
|
||||
// arquivo que faz validação + cálculo + formatação + envio de email
|
||||
export function processarLicenca(dados: DadosLicenca) {
|
||||
validar(dados) // validação
|
||||
const valor = calcular(dados) // cálculo
|
||||
const pdf = gerarPDF(valor) // formatação
|
||||
enviarEmail(pdf) // notificação
|
||||
// 4 razões para mudar = 4 responsabilidades
|
||||
}
|
||||
```
|
||||
|
||||
## Impacto
|
||||
|
||||
Código que viola SOLID se torna cada vez mais caro de manter: cada mudança exige mais esforço e introduz mais risco de regressão.
|
||||
|
||||
## Referências
|
||||
|
||||
- Robert C. Martin — "Agile Software Development, Principles, Patterns, and Practices"
|
||||
- Refactoring.Guru — https://refactoring.guru/pt-br/design-patterns
|
||||
- Persona: `agents/refatorar/persona`
|
||||
|
|
@ -3,9 +3,9 @@ type: rule
|
|||
name: theme-provider-mui-betha
|
||||
description: Define a arquitetura centralizada do ThemeProvider MUI Betha nos frontends React do ecossistema GOV (AUTENTICACAO-FRONT, QUIPO-FRONT, QUIPO-PORTAL3)
|
||||
scope: global
|
||||
trigger: context_match
|
||||
trigger: model_decision
|
||||
priority: alta
|
||||
updatedAt: "2026-07-02"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: ThemeProvider MUI Centralizado — Arquitetura Betha
|
||||
|
|
|
|||
|
|
@ -3,10 +3,9 @@ type: rule
|
|||
name: tsconfig-ignore-deprecations
|
||||
description: Workaround obrigatório para tsup v8.5.0 que injeta baseUrl depreciado no TS 6.0
|
||||
scope: global
|
||||
trigger: file_match
|
||||
globs:
|
||||
- "**/tsconfig.json"
|
||||
updatedAt: "2026-07-01"
|
||||
trigger: glob
|
||||
globs: "**/tsconfig*.json"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: ignoreDeprecations no tsconfig.json
|
||||
|
|
|
|||
|
|
@ -3,11 +3,10 @@ type: rule
|
|||
name: typescript-module-resolution
|
||||
description: Padrão obrigatório de moduleResolution para todos os pacotes do monorepo Azteca
|
||||
scope: global
|
||||
trigger: file_match
|
||||
globs:
|
||||
- "**/tsconfig.json"
|
||||
trigger: glob
|
||||
globs: "**/tsconfig*.json"
|
||||
priority: alta
|
||||
updatedAt: "2026-07-01"
|
||||
updatedAt: "2026-09-28"
|
||||
---
|
||||
|
||||
# Regra: moduleResolution Padrão do Monorepo
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue