1001Ferramentas
🔁Geradores

Gerador de RewriteRule (.htaccess)

Gera regras RewriteRule (mod_rewrite) para .htaccess. Inclui flag [L,R=301,QSA] e suporte a regex com grupos de captura.


  

mod_rewrite no .htaccess: rewrites internos, flags, RewriteCond e os padrões que todo dev deveria memorizar

O mod_rewrite do Apache é um pequeno processador de URLs baseado em regex que roda a cada request. Diferente de um redirect comum, um rewrite é interno: a URL muda dentro do servidor, mas o browser continua vendo o endereço original — pretty URLs, esconder extensões de arquivo, fallback de SPA e hops para reverse proxy são todos rewrites por baixo dos panos. Hops 301/302 visíveis no browser são rewrites com a flag [R] aplicada por cima.

Este gerador emite um único RewriteRule para o par padrão/substituição que você digitou; a referência abaixo cobre a sintaxe completa, todas as flags que valem a pena conhecer, as variáveis de RewriteCond mais usadas, padrões comuns (WordPress, fallback SPA, modo de manutenção, pretty URLs) e o trade-off de performance de rodar regras a partir do .htaccess.

Sintaxe: RewriteEngine, RewriteCond, RewriteRule

RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php?route=$1 [QSA,L]

Linhas RewriteCond se acumulam em cadeia lógica AND e se aplicam apenas ao próximo RewriteRule. Os testes !-f / !-d ("não é arquivo", "não é diretório") são o guard clássico para que arquivos estáticos e diretórios reais escapem do front controller.

Cheat sheet de flags

  • [L] — last; para de processar regras no passo atual.
  • [R=301] — emite redirect externo 301 (aceita qualquer 3xx).
  • [QSA] — query string append; junta a query original com a nova.
  • [NC] — no case; padrão case-insensitive.
  • [NE] — no escape; não faz URL-encode dos caracteres especiais na substituição.
  • [F] — forbidden; retorna 403 sem reescrever a URL.
  • [G] — gone; retorna 410 (use para aposentar URLs definitivamente).
  • [P] — proxy; encaminha o request para um backend (requer mod_proxy).
  • [E=var:val] — define uma variável de ambiente visível ao PHP e ao access log.

Padrões comuns

# Pretty URLs: /produto/42 -> produto.php?id=42
RewriteRule ^produto/(\d+)$ produto.php?id=$1 [L]

# Esconder a extensão .php
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^([^.]+)$ $1.php [L]

# Fallback de SPA (Vue, React, Angular)
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.html [L]

# Modo de manutenção (liberando o seu IP)
RewriteCond %{REMOTE_ADDR} !^198\.51\.100\.42$
RewriteCond %{REQUEST_URI} !^/manutencao\.html$
RewriteRule (.*) /manutencao.html [R=503,L]

# Subdomínio para subpasta: blog.exemplo.com -> exemplo.com/blog
RewriteCond %{HTTP_HOST} ^blog\.exemplo\.com$ [NC]
RewriteRule (.*) /blog/$1 [L]

Variáveis e operadores em RewriteCond

Variáveis úteis: %{REQUEST_URI}, %{REQUEST_FILENAME}, %{HTTP_HOST}, %{HTTPS}, %{HTTP_USER_AGENT}, %{QUERY_STRING}, %{TIME_HOUR}, %{REMOTE_ADDR}. Operadores: ! (negação), = (igualdade de string), </> (lexicográfico), -d (é diretório), -f (é arquivo), -l (é symlink), -s (tamanho > 0). Combine flags depois do padrão com [NC,OR] quando precisar de OR lógico entre duas condições.

Performance e debugging

O Apache lê todo .htaccess do diretório da URL até o document root a cada request, então uma árvore profunda com overrides adiciona latência. Quando você controla o virtual host, mova as regras para <Directory> com AllowOverride None para ganho mensurável. Para debugar, suba o log temporariamente com LogLevel rewrite:trace3 — toda regra que casou, todo grupo de captura e toda substituição são impressos no access log. Ferramentas como htaccess.io e htaccess-checker.com permitem fazer dry-run das regras no browser.

FAQ

Rewrite ou redirect — qual eu quero? Use rewrite quando a URL deve mudar só dentro do servidor (pretty URLs, roteamento de SPA). Use redirect ([R=301]) quando a barra de endereço do browser também precisa mudar (host canônico, HTTPS, URL aposentada).

O .htaccess é lento? Levemente, sim — é relido a cada request. A correção é mover as regras para o config do virtual host e desligar o AllowOverride. O comportamento fica idêntico, só os stat() por request somem.

Como debugar uma regra que não casa? Suba temporariamente LogLevel alert rewrite:trace3 no virtual host. O access log vai imprimir o trace completo do rewrite: quais regras rodaram, o que cada grupo de captura segurou e a URL final. Lembre-se de reduzir o nível depois — trace3 é verboso.

Por que a ordem das regras importa? As regras são processadas de cima para baixo, e [L] só para o passo atual — rewrites internos podem reentrar no pipeline. Coloque as regras mais específicas primeiro e o catch-all (ex. fallback de SPA) por último para que o primeiro match seja o correto.

Ferramentas Relacionadas