DEV Community

Denis Augusto
Denis Augusto

Posted on

Seu code review não precisa discutir espaçamento

O pull request com 14 comentários (13 são sobre vírgula)

Você abre o PR do colega. Quarenta arquivos alterados, uma feature importante.

E os comentários são esses:

"faltou linha em branco antes do return"

"acho que aqui cabia trailing comma"

"aspas simples, né? o resto do projeto usa simples"

"esse import não tá sendo usado"

Enquanto isso, no meio do diff, tem um método recebendo ?User e chamando $user->email sem checar null. Ninguém viu. Todo mundo estava ocupado contando espaço.

Esse é o custo real da falta de automação: não é o tempo gasto com detalhe, é a atenção que sobra pra revisar o que importa.

E tem o lado humano. Ninguém gosta de receber cinco comentários sobre estilo. Cria atrito onde não precisa ter.

Três ferramentas resolvem isso. Trinta minutos de setup.

1. Pint — o fim da discussão sobre estilo

O Pint já vem instalado em projetos Laravel novos. Se o seu é antigo:

composer require laravel/pint --dev
Enter fullscreen mode Exit fullscreen mode

E roda:

./vendor/bin/pint
Enter fullscreen mode Exit fullscreen mode

Pronto. Ele formata o projeto inteiro seguindo o padrão Laravel. Aspas, espaçamento, ordem de import, trailing comma — tudo resolvido sem ninguém opinar.

Se quiser ajustar alguma coisa, cria um pint.json na raiz:

{
    "preset": "laravel",
    "rules": {
        "declare_strict_types": true,
        "ordered_imports": { "sort_algorithm": "alpha" }
    }
}
Enter fullscreen mode Exit fullscreen mode

Dois flags que valem ouro no dia a dia:

./vendor/bin/pint --dirty   # só o que você mexeu (rápido)
./vendor/bin/pint --test    # não muda nada, só falha se estiver fora do padrão
Enter fullscreen mode Exit fullscreen mode

O --test é o que vai pro CI.

Aviso importante: rode o Pint no projeto inteiro em um commit isolado, sozinho, antes de tudo. Se você misturar formatação com mudança de lógica, o diff fica ilegível e o git blame vira sopa.

2. Larastan — o bug que aparece antes do deploy

Aqui o jogo muda de nível. O Larastan (PHPStan com esteroides de Laravel) lê seu código sem executar e aponta erro de tipo, método que não existe, variável possivelmente nula.

composer require --dev "larastan/larastan:^3.0"
Enter fullscreen mode Exit fullscreen mode

Cria o phpstan.neon na raiz:

includes:
    - vendor/larastan/larastan/extension.neon

parameters:
    paths:
        - app/
        - routes/

    level: 5
Enter fullscreen mode Exit fullscreen mode

E roda:

./vendor/bin/phpstan analyse
Enter fullscreen mode Exit fullscreen mode

Na primeira execução ele vai encontrar coisa. Muita coisa. Não entra em pânico e nem tenta corrigir tudo hoje.

Comece no nível 0 ou 1. Sério. Zera os erros nesse nível, sobe pro próximo, zera de novo. Um nível por sprint é um ritmo saudável. Level 5 já pega a maioria dos problemas de verdade; do 6 pra cima começa a exigir docblock em tudo.

E se o projeto for grande demais pra começar do zero, tem a saída elegante:

./vendor/bin/phpstan analyse --generate-baseline
Enter fullscreen mode Exit fullscreen mode

Ele guarda todos os erros atuais num arquivo e passa a ignorá-los. A partir de agora, código novo não pode introduzir erro novo. A dívida antiga fica lá, congelada, e você paga aos poucos.

O que ele pega e o code review não pega:

// Larastan: "Cannot call method email() on User|null"
$user = User::find($id);
Mail::to($user->email)->send(...);   // 💥 em produção quando não achar

// Larastan: "Call to an undefined method App\Models\Pedido::pagos()"
Pedido::pagos()->get();   // você renomeou o scope e esqueceu daqui
Enter fullscreen mode Exit fullscreen mode

Esse segundo é ouro puro em refatoração.

3. Rector — refatoração automática

O Rector reescreve código pra você. É o que você usa quando sobe de versão do PHP ou do Laravel e não quer varrer 800 arquivos na mão.

composer require rector/rector --dev
Enter fullscreen mode Exit fullscreen mode

rector.php na raiz:

<?php

use Rector\Config\RectorConfig;

return RectorConfig::configure()
    ->withPaths([
        __DIR__ . '/app',
        __DIR__ . '/tests',
    ])
    ->withPhpSets()                        // moderniza pra sua versão do PHP
    ->withPreparedSets(deadCode: true)     // remove código morto
    ->withComposerBased(laravel: true);    // regras específicas de Laravel
Enter fullscreen mode Exit fullscreen mode

Sempre rode em dry-run primeiro:

./vendor/bin/rector --dry-run   # mostra o que faria
./vendor/bin/rector             # aplica
Enter fullscreen mode Exit fullscreen mode

O que ele faz sozinho: converte construtor antigo pra property promotion, troca array() por [], transforma if/else em operador ternário quando cabe, adiciona tipo de retorno, remove use não usado, atualiza chamadas descontinuadas do Laravel.

Uma tarde de Rector num projeto legado economiza semanas. Só faz duas coisas: tenha testes e commit separado — igual ao Pint.

Colocando pra rodar sozinho

De nada adianta se depender de alguém lembrar. Dois lugares:

No CI, um job que não deixa passar:

  qualidade:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: shivammathur/setup-php@v2
        with:
          php-version: '8.4'
      - run: composer install --prefer-dist --no-interaction
      - run: ./vendor/bin/pint --test
      - run: ./vendor/bin/phpstan analyse --error-format=github
Enter fullscreen mode Exit fullscreen mode

Repara que o Rector não está aí. Ele é ferramenta de refatoração pontual, não de validação contínua — deixa ele fora do CI, você roda quando precisa.

No pre-commit, pra você nem ver o erro chegar:

# .git/hooks/pre-commit
#!/bin/sh
./vendor/bin/pint --dirty
git add $(git diff --name-only --cached | grep '\.php$')
Enter fullscreen mode Exit fullscreen mode

Formata só o que mudou e já adiciona ao commit. Você nunca mais commita código fora do padrão — e nem percebe que isso aconteceu.

A pegadinha: ferramenta não substitui revisão

Vale deixar claro, porque tem gente que liga tudo isso e acha que resolveu code review.

Não resolveu. Pint, Larastan e Rector não sabem se o nome da sua classe faz sentido, se a regra de negócio está certa, se aquela query vai derrubar o banco com 100 mil registros ou se você acabou de criar uma falha de autorização.

Eles só limpam o ruído pra que a revisão humana sobre pro que só humano faz. Que é justamente o que você quer.

Bônus: um comando pra tudo

Coloca no composer.json e a vida fica mais fácil:

"scripts": {
    "qa": [
        "./vendor/bin/pint",
        "./vendor/bin/phpstan analyse",
        "php artisan test"
    ]
}
Enter fullscreen mode Exit fullscreen mode

Agora é composer qa antes de abrir qualquer PR. ✅

Antes de você fechar a aba

O objetivo não é ter código perfeito. É parar de gastar energia humana com coisa que máquina resolve.

Se você tiver tempo pra só uma hoje, instala o Pint. São dois comandos e o retorno é imediato — na próxima revisão, ninguém mais vai comentar sobre vírgula.

Seu projeto já usa alguma dessas? E qual foi o erro mais bizarro que o PHPStan achou pra você? Conta nos comentários — os melhores são sempre naquele arquivo que "funcionava bem há três anos".


Top comments (0)