Seis ADRs no formato Archgate fundamentados nas evidências do estudo — com arquivos .rules.ts companheiros e regras de lint customizadas prontas para soltar em um codebase no estilo Sentry.
Esta página resume seis Architecture Decision Records fundamentados nas conclusões do estudo. Cada ADR é publicado como um artefato completo no repositório do estudo, formatado para corresponder à convenção de ADRs do Archgate — frontmatter, seções e (quando aplicável) um arquivo .rules.ts companheiro que implementa verificações determinísticas. Para o schema autoritativo de ADRs e o guia de autoria de regras, consulte cli.archgate.dev.
Por que o formato Archgate?
Seção intitulada “Por que o formato Archgate?”O Archgate é o projeto que hospeda este estudo. Sua convenção de ADRs é opinativa por um motivo: todo ADR tem um frontmatter parseável (id, domínio, globs de arquivo escopados), seções estruturadas (Contexto com alternativas, Decisão, Do’s and Don’ts, Padrão de implementação, Consequências, Conformidade e Enforcement) e um arquivo .rules.ts companheiro opcional que o motor archgate check pode executar para aplicar as regras automaticamente.
Ao publicar as propostas no formato Archgate, a equipe do Sentry (ou qualquer equipe que rode o Archgate) poderia literalmente soltar esses arquivos em .archgate/adrs/ e começar a aplicá-los imediatamente.
Os arquivos
Seção intitulada “Os arquivos”Todos os arquivos de ADR vivem em studies/sentry-pr-review-friction/proposed-adrs/:
| Arquivo | Domínio | Tem regras |
|---|---|---|
GEN-001-pr-scope-boundaries.md + .rules.ts | general | Sim |
BE-001-api-contract-evolution.md + .rules.ts | backend | Sim |
GEN-002-test-evidence-matrix.md + .rules.ts | general | Sim |
FE-001-frontend-component-conventions.md + .rules.ts | frontend | Sim |
BE-002-security-review-protocol.md + .rules.ts | backend | Sim |
GEN-003-bot-finding-promotion.md | general | Não (ADR de workflow) |
Mais regras de lint customizadas em proposed-lint-rules/:
| Arquivo | Ferramenta | Alvos |
|---|---|---|
eslint-frontend-conventions.js | ESLint | Estilos inline, Stack gap=0, try/finally de estado assíncrono |
semgrep-doesnotexist.yaml | Semgrep | Tratamento ausente de Model.DoesNotExist |
semgrep-filter-first-unreachable.yaml | Semgrep | .filter().first() com except DoesNotExist inalcançável |
semgrep-high-cardinality-metrics.yaml | Semgrep | Tags de métricas de alta cardinalidade |
semgrep-direct-dict-access-api.yaml | Semgrep | Acesso direto a dict em respostas de API externas |
As regras de lint são projetadas para serem instaladas em .archgate/lint/ segundo a convenção de pasta de lint do Archgate. Consulte cli.archgate.dev para detalhes.
Resumo de cada ADR
Seção intitulada “Resumo de cada ADR”GEN-001 — Limites de escopo de PR e orçamento de tamanho
Seção intitulada “GEN-001 — Limites de escopo de PR e orçamento de tamanho”Problema: PRs grandes (≥10 arquivos ou ≥400 de churn) atingem o quartil de alto atrito 57,4% das vezes contra 9,8% para PRs minúsculos.
Decisão: limites de tamanho flexíveis (≤5 arquivos, ≤200 de churn) com seção obrigatória de “Scope Rationale” na descrição do PR para PRs acima do limite. Limiar rígido no corte empírico de PR grande.
Regras (GEN-001-pr-scope-boundaries.rules.ts):
pr-size-warning— alerta quando o limiar flexível ou rígido é excedidoscope-rationale-required— bloqueia o merge se um PR acima do limite não tiver a seção Scope Rationale
BE-001 — Evolução de contrato de API e configuração
Seção intitulada “BE-001 — Evolução de contrato de API e configuração”Problema: design de API e valores padrão é o principal tema de discussão (38,3% dos PRs de alto atrito). Achados recorrentes de bots incluem UnionType str | None no registro de opções, divergências de Literal do Pydantic e divergências de chave de opção entre escritor/leitor.
Decisão: tipos callable concretos no registro de opções; constantes de chave tipadas em um único registro; defaults None exigem explicação semântica; opções conflitantes rejeitadas em tempo de validação.
Regras (BE-001-api-contract-evolution.rules.ts):
no-union-type-in-option-registration— sinaliza padrõestype=str | Noneoption-keys-must-use-constants— sinaliza chaves de opção como literais de string em chamadasoptions.get/setno-none-default-without-nullable-comment— exige comentário explicando a semântica deNone
GEN-002 — Matriz de evidência de testes por tipo de mudança
Seção intitulada “GEN-002 — Matriz de evidência de testes por tipo de mudança”Problema: evidência de testes está empatada como principal tema de discussão (38,3%). Revisores e bots pedem testes específicos (caminhos de erro, casos extremos, valores sentinela) — não apenas “mais testes”.
Decisão: matriz de testes por tipo de mudança com cenários mínimos explícitos para cada tipo de mudança (novo endpoint, componente modificado, tratamento de erro, migração etc.). A descrição do PR deve incluir uma seção Test Plan mapeando a mudança para entradas da matriz.
Regras (GEN-002-test-evidence-matrix.rules.ts):
test-plan-section-required— a descrição do PR deve incluir## Test Plantest-plan-references-must-exist— os nomes de testes listados no plano devem ser encontrados nos arquivos de teste alteradosno-bare-except-pass-in-tests—except: passsolto em arquivos de teste indica asserção ausente
FE-001 — Convenções de componentes e estilização de frontend
Seção intitulada “FE-001 — Convenções de componentes e estilização de frontend”Problema: padrões de componentes aparecem em 35,0% dos PRs de alto atrito. O comentário de revisão mais repetido em todo o conjunto de dados — “can we avoid this inline style w/ prop of some kind?” — apareceu 6 vezes só no PR #111529.
Decisão: sem props style= inline (com comentário de escape hatch); design system primeiro; regras de seleção de componente de layout; try/finally para estado de carregamento assíncrono.
Regras (FE-001-frontend-component-conventions.rules.ts):
no-inline-style— sinalizastyle=em JSX sem comentário de escape hatchno-stack-with-zero-gap— sinaliza<Stack gap={0}>async-state-try-finally— alerta quando o setter de estado de carregamento reinicia notrymas não nofinally
Plugin de ESLint companheiro (eslint-frontend-conventions.js) fornece feedback na IDE em tempo de edição para os mesmos padrões.
BE-002 — Protocolo de revisão de segurança para mudanças de auth e integração
Seção intitulada “BE-002 — Protocolo de revisão de segurança para mudanças de auth e integração”Problema: a discussão de segurança aparece em 20% dos PRs de alto atrito, mas com riscos desproporcionais. O escopo github tem a maior mediana de contagem de revisões (5,5) de qualquer escopo devido à superfície de segurança do pipeline de OAuth.
Decisão: PRs que tocam caminhos de auth/integração/API devem incluir uma seção Security Considerations respondendo a cinco perguntas obrigatórias; atribuição de revisor de segurança orientada por CODEOWNERS; sem remoção silenciosa de defense-in-depth; IDs fornecidos pelo usuário validados antes da vinculação de estado do pipeline.
Regras (BE-002-security-review-protocol.rules.ts):
security-considerations-section-required— PRs que tocam caminhos sensíveis devem ter a seçãono-pipeline-bind-before-validation—pipeline.bind_state()deve seguir as verificações de autorizaçãono-unscoped-model-get-in-api— sinalizaModel.objects.get()em endpoints de API sem escopo de organização
GEN-003 — Converter achados recorrentes de bots em regras determinísticas
Seção intitulada “GEN-003 — Converter achados recorrentes de bots em regras determinísticas”Problema: revisores bot (sentry[bot], sentry-warden[bot], cursor[bot]) encontram bugs reais, mas as mesmas categorias de bug se repetem entre os PRs. Veja a página de Atrito de revisão automatizada para o catálogo completo de padrões.
Decisão: rastrear categorias de achados de bots. Quando uma categoria acumula ≥3 ocorrências em 90 dias, comprometer-se a promovê-la para uma verificação determinística (modo strict do mypy, regra de lint de AST, validação de schema/registro ou fixture de teste). Suprimir a categoria do bot uma vez que a verificação entre em produção, liberando o bot para encontrar padrões genuinamente novos.
Regras: este é um ADR de workflow — sem .rules.ts companheiro. O enforcement é procedural via a revisão trimestral de promoção e o rastreador de achados de bots. Os outros cinco ADRs acima (BE-001, BE-002, FE-001) e as regras de lint propostas são, eles próprios, o resultado de aplicar o GEN-003 aos achados de bots neste estudo.
Resumo de impacto
Seção intitulada “Resumo de impacto”| ADR | Tema(s) alvo | Cobertura de PRs de alto atrito | Mecanismo |
|---|---|---|---|
| GEN-001 | Atrito orientado por tamanho | 57,4% dos PRs grandes | Reduzir tamanho do PR + forçar rationale de escopo |
| BE-001 | Design de API (38,3%) + gerenciamento de estado (35,0%) | ~40% | Registros tipados + tipos callable concretos |
| GEN-002 | Evidência de testes (38,3%) + segurança de tipos (30,0%) | ~40% | Matriz de testes por tipo de mudança no template de PR |
| FE-001 | Padrões de componentes (35,0%) + nomenclatura (11,7%) | ~35% | Regras de ESLint eliminando comentários recorrentes de estilo |
| BE-002 | Segurança (20,0%) | ~20% | Análise de segurança antecipada + gating por CODEOWNERS |
| GEN-003 | Atrito de revisão de bots (68,3%) | ~68% | Promover achados agênticos recorrentes para verificações determinísticas |
Prioridade de implementação
Seção intitulada “Prioridade de implementação”-
FE-001 (Convenções de frontend) — menor custo, maior sinal imediato. O plugin de ESLint para estilos inline elimina o comentário de revisão mais repetido do nosso conjunto de dados. Ganho rápido.
-
GEN-001 (Limites de escopo de PR) — alto impacto, custo moderado. A regra de aviso de tamanho é fácil de implementar e mira diretamente o preditor de atrito mais forte.
-
GEN-003 + as regras de lint (Promoção de achados de bots) — maior alavancagem de longo prazo. As 4 regras de Semgrep em
proposed-lint-rules/poderiam entrar em produção em dias e imediatamente suprimir as categorias mais comuns de achados de bots. -
GEN-002 (Matriz de evidência de testes) — custo médio, alto impacto em clareza. A matriz pode ser publicada como uma mudança de template de PR e imediatamente referenciada pelos revisores.
-
BE-001 (Evolução de contrato de API) — custo mais alto, alto impacto de longo prazo. Migrar para um registro tipado de chaves de opção é uma refatoração significativa, mas elimina permanentemente uma classe inteira de bugs.
-
BE-002 (Protocolo de segurança) — especializado, mas crítico. Afeta cerca de 20% dos PRs, mas esses PRs carregam o maior risco de descuido de segurança.
Como usar esses ADRs
Seção intitulada “Como usar esses ADRs”Se você roda um codebase no estilo Sentry (backend em Python + frontend em TypeScript) e quer adotar essas propostas:
# 1. Initialize archgate in your repo (if not already)cd your-repoarchgate init
# 2. Drop the ADR files into .archgate/adrs/cp /path/to/study/proposed-adrs/*.md .archgate/adrs/cp /path/to/study/proposed-adrs/*.rules.ts .archgate/adrs/
# 3. Drop the lint rules into .archgate/lint/mkdir -p .archgate/lint/semgrepcp /path/to/study/proposed-lint-rules/eslint-frontend-conventions.js .archgate/lint/eslint.jscp /path/to/study/proposed-lint-rules/semgrep-*.yaml .archgate/lint/semgrep/
# 4. Adjust the file globs in each ADR's frontmatter to match your repo layout
# 5. Run the checksarchgate checkCada ADR é independente — você pode adotá-los um de cada vez, na ordem de prioridade acima, sem se comprometer com o pacote completo de antemão. Para a referência completa de comandos, consulte cli.archgate.dev.