
então eu tenho essa configuração do Apache onde estou tentando "reescrever" os usuários em uma página de erro personalizada, mas não está funcionando. Entrei http://localhost/index.html/ddgdg%:sdsdfs
no navegador e não recebi minha página de erro.
Posso visualizar a página de erro personalizada inserindo diretamente seu URL no navegador ( http://localhost/my-error.html
).
Alguma idéia do que eu poderia estar fazendo de errado?
meu httpd.conf completo:link para httpd.conf
minhas alterações no httpd.conf padrão(Eu também tive que descomentar o LoadModule para mod_rewrite.so)
RewriteEngine On
LogLevel alert rewrite:info
#if invalid characters are present in the URI, display 404 page
RewriteCond %{REQUEST_URI} ^\/.+[:%].+
RewriteRule "^/$" "http://%{SERVER_NAME}/my-error.html" [L,R=301]
conteúdo da página de erro personalizada
$ cat /Library/WebServer/Documents/my-error.html
<html><body><h1>404 error here</h1></body></html>
versão apache
$ apachectl -v
Server version: Apache/2.4.34 (Unix)
Server built: Feb 22 2019 20:20:11
editar1:Executando o macOS Mojave no momento, mas configurará uma VM Ubuntu em algum momento.
Responder1
Há alguns problemas diferentes acontecendo aqui ...
http://localhost/index.html/ddgdg%:sdsdfs
Na verdade, você não declarou qual resposta está obtendo, apenas o que énão está acontecendo. No entanto, devido ao desvio %
(não precedendo um octeto codificado em hexadecimal), este URL é estritamente inválido e eu esperaria que o Apache respondesse com um 400 Bad Request
. A única maneira de substituir isso é criar um documento de erro 400 personalizado no qual você verifica o URL solicitado e personaliza a resposta. Por exemplo:
ErrorDocument 400 /my-error.html
Se não fosse pelo erro, %
você deveria ser capaz de capturar essa solicitação usando mod_rewrite e redirecionar de acordo. No entanto, você RewriteRule
está verificando um caminho de URL vazio (ou seja, "^/$"
), enquanto o URL solicitado no seu exemplo está longe de estar vazio (ou seja, /index.html/ddgdg%:sdsdfs
) - portanto, a RewriteRule
diretiva nunca corresponderá ao seu URL de exemplo. Para verificar %
ou :
em qualquer lugar do caminho da URL e redirecionar, você pode fazer algo como o seguinte:
# Checks for a "%" or ":" in the URL-path
RewriteRule [%:] /my-error.html [L,R=302]
Mas observe que o caminho da URL correspondente aoRewriteRule
padrão(assim como a REQUEST_URI
variável do servidor) já está% decodificado, portanto, isso corresponderá apenas a URLs onde caracteres especiais foram codificados duplamente (raro). (Conforme observado acima, um desvio %
provavelmente gerará uma resposta 400antesmod_rewrite é capaz de processar a solicitação.)
Eu também questionaria por que você deseja "redirecionar" para o seu documento de erro personalizado (ou seja, my-error.html
) e não atendê-lo diretamente? O redirecionamento tem uma série de desvantagens: resposta 3xx enviada ao cliente, perda de informações sobre a URL que causou o erro, duplicação das solicitações ao seu servidor, etc.
Você poderiareescrever internamentea solicitação para /my-error.html
, em vez de redirecionar, simplesmente removendo o R
sinalizador. Por exemplo:
RewriteRule [%:] /my-error.html [L]
Mas, a menos que você defina manualmente o status HTTP, my-error.html
o usuário verá uma 200 OK
resposta - o que não é desejável.
OU (de preferência) crie um 404 personalizado (que se parece com o que você está tentando fazer) e acione-o. Por exemplo:
ErrorDocument 404 /my-error.html
RewriteRule [%:] - [R=404]
O Apache então define o status de resposta HTTP "404 Not Found".
No entanto, você provavelmente não precisa usar mod_rewrite aqui. No seu URL de exemplo, tudo o que vem depois index.html
do caminho da URL, ou seja /ddgdg%:sdsdfs
, éinformações adicionais do nome do caminho(também conhecido como path-info / PATH_INFO
). Por padrão, o manipulador que processa respostas de texto/html não permite path-info e acionará implicitamente um 404 (se não fosse pelo extraviado %
- como discutido acima), chamando seu custom ErrorDocument
(se definido). Portanto, a RewriteRule
diretiva do último exemplo pode simplesmente ser removida, já que o Apache irá acionar um 404 de qualquer maneira (a menos que você substitua esse comportamento por AcceptPathInfo
).