GitHub Copilot com Pre-Commit Hooks: Padrões Sugeridos
🔍 WiseChecker

GitHub Copilot com Pre-Commit Hooks: Padrões Sugeridos

Desenvolvedores que usam GitHub Copilot frequentemente geram código que não segue as regras de lint, formatação ou segurança do projeto. Pre-commit hooks capturam esses problemas antes que um commit chegue ao repositório remoto. O desafio é que as sugestões do Copilot podem ignorar esses hooks se o desenvolvedor commitar o código gerado sem revisão. Este artigo explica como configurar pre-commit hooks para validar código gerado pelo Copilot, sugere padrões de hooks que visam saídas comuns do Copilot e mostra como integrar o Copilot com fluxos de trabalho orientados por hooks. Você aprenderá configurações concretas de hooks para projetos Python, JavaScript e TypeScript.

Principais Conclusões: Validando Código do Copilot com Pre-Commit Hooks

  • Diretório de hooks do framework pre-commit: Um registro central de hooks prontos para uso que aplicam verificações de lint, formatação e segurança em cada commit.
  • .pre-commit-config.yaml: O arquivo de configuração onde você define hooks para linguagens como Python, JavaScript e TypeScript.
  • Fluxo de revisão do Copilot: Execute hooks antes do commit e revise manualmente as sugestões do Copilot para capturar falsos positivos e erros de lógica.

Como os Pre-Commit Hooks Interagem com Código Gerado pelo Copilot

Pre-commit hooks são scripts que são executados automaticamente antes de um commit ser finalizado. Eles verificam arquivos em staged para problemas como erros de sintaxe, violações de estilo ou vulnerabilidades de segurança. Quando um desenvolvedor aceita uma sugestão do Copilot e coloca esse arquivo em staged, o hook é executado na versão em staged. Se o hook falhar, o commit é bloqueado até que o desenvolvedor corrija o problema. Isso impede que código gerado com falhas entre no repositório.

A interação tem dois aspectos principais. Primeiro, o Copilot frequentemente gera código que não corresponde ao guia de estilo existente do projeto. Por exemplo, pode usar aspas simples em um projeto JavaScript que exige aspas duplas. Um hook de formatação como Prettier captura isso. Segundo, o Copilot pode introduzir imports ou variáveis não utilizadas, especialmente ao sugerir grandes blocos de código. Um hook de lint como ESLint ou Flake8 sinaliza esses casos. O desenvolvedor então revisa e corrige a sugestão antes de commitar.

Um equívoco comum é que os hooks tornam o Copilot inutilizável. O oposto é verdadeiro. Os hooks atuam como uma rede de segurança, capturando problemas que o desenvolvedor pode perder durante uma revisão rápida. O desenvolvedor ainda pode aceitar sugestões do Copilot, executar os hooks e corrigir quaisquer violações. Esse fluxo de trabalho mantém o repositório limpo enquanto permite que o desenvolvedor se beneficie da velocidade do Copilot.

Padrões de Hook Sugeridos para Validação de Código do Copilot

Os padrões a seguir focam nos problemas mais comuns que o código gerado pelo Copilot introduz. Cada padrão inclui uma configuração de hook e uma explicação de por que é importante para a saída do Copilot.

Padrão 1: Aplicar Formatação Consistente com Prettier

O Copilot não respeita as regras de formatação do seu projeto. Ele usa sua própria distribuição de treinamento, que pode usar estilos de aspas diferentes, vírgulas finais ou indentação. O Prettier reformata todo o código em staged para corresponder à configuração do projeto. Adicione isso ao seu .pre-commit-config.yaml:

- repo: https://github.com/pre-commit/mirrors-prettier
  rev: v3.0.0
  hooks:
    - id: prettier
      args: [--config, .prettierrc]

O campo args aponta para o arquivo de configuração do Prettier do seu projeto. Este hook é executado em arquivos JavaScript, TypeScript, CSS, JSON e Markdown. Ele reformata o arquivo no local, para que o desenvolvedor veja a versão formatada antes do commit ser concluído.

Padrão 2: Remover Imports e Variáveis Não Utilizadas com ESLint

O Copilot frequentemente adiciona imports que o código gerado não usa. Isso acontece porque o Copilot prevê o próximo token sem entender o contexto completo do arquivo. O ESLint com a regra no-unused-vars captura esses casos. Adicione este hook:

- repo: https://github.com/pre-commit/mirrors-eslint
  rev: v8.50.0
  hooks:
    - id: eslint
      args: [--fix, --config, .eslintrc.js]
      types: [javascript]

A flag --fix instrui o ESLint a remover automaticamente imports e variáveis não utilizadas. Se o ESLint não conseguir corrigir uma violação de regra, ele falha o commit e mostra o erro. O desenvolvedor então corrige manualmente a sugestão do Copilot.

Padrão 3: Detectar Segredos Hardcoded com detect-secrets

O Copilot pode sugerir código que contém chaves de API, senhas ou tokens hardcoded. Isso é especialmente arriscado quando o Copilot gera arquivos de configuração ou dados de teste. O hook detect-secrets escaneia arquivos em staged em busca de possíveis segredos. Adicione este hook:

- repo: https://github.com/Yelp/detect-secrets
  rev: v1.4.0
  hooks:
    - id: detect-secrets
      args: [--baseline, .secrets.baseline]

Execute detect-secrets scan uma vez para criar um arquivo de baseline que exclui falsos positivos conhecidos. Depois disso, o hook sinaliza apenas novos segredos. Se o Copilot gerar uma linha que parece um segredo, o hook falha e o desenvolvedor deve substituir o valor hardcoded por uma variável de ambiente.

Padrão 4: Verificar Cabeçalhos de Licença com add-license

Alguns projetos exigem um cabeçalho de licença em cada arquivo fonte. O Copilot não adiciona cabeçalhos. O hook add-license insere o cabeçalho se estiver faltando. Adicione este hook:

- repo: https://github.com/nicoddemus/add-license
  rev: v1.0.0
  hooks:
    - id: add-license
      args: [--license, LICENSE]
      types: [python]

O hook lê o texto da licença de um arquivo chamado LICENSE e o prefixa a qualquer arquivo que não o tenha. Isso garante que arquivos gerados pelo Copilot estejam em conformidade com os requisitos de licenciamento do projeto.

Padrão 5: Validar Tipos TypeScript com tsc

O Copilot pode gerar código TypeScript que usa tipos incorretos ou definições de tipo ausentes. Executar o compilador TypeScript como um pre-commit hook captura erros de tipo. Adicione este hook:

- repo: https://github.com/pre-commit/mirrors-typescript
  rev: v5.2.2
  hooks:
    - id: tsc
      args: [--noEmit, --project, tsconfig.json]

A flag --noEmit instrui o compilador a verificar tipos sem gerar arquivos de saída. Se o Copilot sugerir uma função com tipos incompatíveis, o hook falha e mostra a mensagem de erro. O desenvolvedor então ajusta as anotações de tipo.

Problemas Comuns e Como Lidar com Eles

Mesmo com hooks configurados adequadamente, você pode encontrar problemas específicos ao usar o Copilot com pre-commit hooks. As subseções a seguir abordam os cenários mais frequentes.

Copilot Sugere Código que Passa nos Hooks mas Tem Erros de Lógica

Pre-commit hooks verificam sintaxe, formatação e estilo. Eles não verificam a correção. Uma sugestão do Copilot que passa em todos os hooks ainda pode conter um erro de lógica, como um loop off-by-one ou um algoritmo incorreto. O desenvolvedor deve revisar manualmente o código gerado. Uma boa prática é executar o conjunto de testes do projeto após o commit. Se o conjunto de testes for rápido, adicione-o como um pre-commit hook usando um ponto de entrada personalizado. Por exemplo, use entry: pytest para projetos Python. Isso captura erros de lógica antes do commit ser finalizado.

Hooks Bloqueiam Commits que Incluem Boilerplate Gerado pelo Copilot

O Copilot frequentemente gera código boilerplate, como declarações de import, definições de classe ou fixtures de teste. Alguns hooks, como o hook de cabeçalho de licença, podem falhar porque o arquivo gerado não possui o cabeçalho. Outros hooks, como o hook de import não utilizado, podem falhar porque o Copilot adicionou imports não utilizados. O desenvolvedor deve executar os hooks com a flag --fix quando possível. Para hooks que não podem corrigir automaticamente, o desenvolvedor deve editar manualmente o arquivo. Para reduzir o atrito, configure hooks para corrigir automaticamente os problemas mais comuns. Por exemplo, ESLint com --fix remove imports não utilizados automaticamente.

Copilot Gera Código que Viola Regras Personalizadas do ESLint

Se seu projeto usa regras personalizadas do ESLint, o Copilot pode gerar código que as viola. Por exemplo, uma regra que proíbe console.log sinalizará declarações de depuração geradas pelo Copilot. O desenvolvedor deve revisar a sugestão do Copilot e remover as declarações de depuração antes de commitar. Se a violação for intencional, o desenvolvedor pode adicionar um comentário de desativação do ESLint e documentar o motivo. No entanto, evite desativar regras para código gerado pelo Copilot como hábito. Isso anula o propósito do hook.

Configuração de Pre-Commit Hook vs Revisão Manual: Principais Diferenças

Item Configuração de Pre-Commit Hook Apenas Revisão Manual
Velocidade Automatizada, executa em segundos Mais lenta, depende da disponibilidade do revisor
Consistência Aplica as mesmas regras a cada commit Varia conforme a atenção e experiência do revisor
Cobertura Captura formatação, imports não utilizados, segredos Captura erros de lógica, problemas de design
Atrito para o desenvolvedor Pode bloquear commits até que correções sejam aplicadas Sem bloqueio automático, mas problemas podem chegar à produção
Melhor para Aplicar estilo de código e políticas de segurança Validar correção e arquitetura

Conclusão

Agora você pode configurar pre-commit hooks para validar código gerado pelo Copilot quanto a formatação, imports não utilizados, segredos, cabeçalhos de licença e tipos TypeScript. Os cinco padrões neste artigo cobrem os problemas mais comuns que o Copilot introduz. Comece adicionando os hooks Prettier e ESLint ao seu arquivo .pre-commit-config.yaml. Execute pre-commit install para ativar os hooks. Para validação avançada, adicione o hook do compilador TypeScript e o hook detect-secrets. Sempre revise manualmente as sugestões do Copilot para capturar erros de lógica que os hooks não conseguem detectar.