Você ainda não declarou a (s) URL (s) que está solicitando para acionar o loop de redirecionamento?
No entanto, nas diretivas que você postou, parece que qualquer solicitação do formulário /blog<anything>
ou /ftp<anything>
resultaria em um loop de redirecionamento.
RewriteRule ^blog/?(.*)$ //blog.czghost.czlh/$1 [R=301] RewriteRule ^ftp/?(.*)$ //ftp.czghost.czlh/$1 [R=301]
O mod_rewrite do Apache não suporta URLs relativas a protocolos na RewriteRule
substituição - elas são simplesmente vistas como relativas à raiz (ou seja, um caminho de URL relativo à raiz do documento). Você supostamente vê o resultado desse loop de redirecionamento na barra de endereços do seu navegador? Vai ser algo assim:
- Solicitação inicial:
http://example.com/blog/xyz
- Redireciona para
http://example.com//blog.czghost.czlh/xyz
- Redireciona para
http://example.com//blog.czghost.czlh/.czghost.czlh/xyz
- Redireciona para
http://example.com//blog.czghost.czlh/.czghost.czlh/.czghost.czlh/xyz
- etc.
Você precisa incluir o protocolo. Por exemplo:
RewriteRule ^blog/?(.*)$ https://blog.czghost.czlh/$1 [R=301,L]
Eu também incluí o sinalizador L
( last
), pois você deseja que o redirecionamento seja acionado imediatamente, e não corre o risco de ser reescrito novamente. Isso deve vir antes da reescrita interna (que reescreve a index.php
).
Você precisará limpar o cache do navegador, pois o redirecionamento 301 ( permanente ) errôneo será armazenado em cache pelo navegador. Pode ser mais fácil testar com redirecionamentos 302 (temporários) por esse motivo.
Suas regras blog
e ftp
podem ser manipuladas por uma única diretiva, usando alternação . Por exemplo:
RewriteRule ^(blog|ftp)/?(.*)$ https://$1.czghost.czlh/$2 [R=301,L]
RewriteRule ^[a-z]{2,3}/$ /index.php?lang=$1
Você não tem um grupo de captura (ou seja, subpadrão entre parênteses) no padrão RewriteRule
, portanto, a referência anterior $1
sempre estará vazia. Isso deve ser reescrito como:
RewriteRule ^([a-z]{2,3})/$ /index.php?lang=$1 [L]
Novamente, incluímos o L
flag, para evitar mais reescritas. Observe que isso espera que haja um sufixo de barra no final do caminho da URL. Portanto, somente as URLs do formulário /blog/en/
(com um sufixo de barra) seriam reescritas com êxito (embora talvez isso não esteja relacionado).
Então, em resumo, isso deve ser reescrito como:
RewriteRule ^(blog|ftp)/?(.*)$ https://$1.czghost.czlh/$2 [R=301,L]
RewriteRule ^([a-z]{2,3})/$ /index.php?lang=$1 [L]
Also, if user writes in
index.php?lang=$1
, I need to redirect him to the nice URL variant instead.
Você pode fazer isso com um redirecionamento adicional antes das diretivas acima. Por exemplo:
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{QUERY_STRING} ^lang=([a-z]{2,3})$
RewriteRule ^(index\.php)?$ /%1/? [R=301,L]
Você precisa usar uma diretiva RewriteCond
para verificar a string de consulta na variável QUERY_STRING
server (isso não pode ser feito na diretiva RewriteRule
). A verificação anterior na variável de ambiente REDIRECT_STATUS
é para garantir que processamos somente solicitações iniciais e não solicitações reescritas pela última diretiva que reconfigura a URL para /index.php?lang=xyz
. O REDIRECT_STATUS
env var está vazio na solicitação inicial, mas é definido como "200" (como em 200 OK - status HTTP) após a primeira reescrita bem-sucedida .
Isso corresponderá a index.php
ou a um caminho de URL vazio (por exemplo, /?lang=xyz
). %1
é uma referência retroativa ao último CondPattern (em oposição a $N
que é uma referência anterior ao padrão RewriteRule
). O ?
no final da RewriteRule
substituição é necessário para remover a string de consulta da URL redirecionada (alternativamente, você pode usar a flag QSD
no Apache 2.4 +). / p>
Novamente, é melhor testar primeiro com um redirecionamento 302 (temporário) que não será armazenado em cache pelo navegador.
(From comments:) The only thing that works properly, is the
/ftp/
redirect./blog/
redirect stays with unchanged URL in a blank page
Você deve se certificar de que não exista nenhum diretório físico no sistema de arquivos com o mesmo nome, ex. %código%. E que esse subdiretório não tem um arquivo /blog
adicional que pode estar substituindo isso. Além disso, certifique-se de que não exista um arquivo que compartilhe o mesmo nome de base .htaccess
. por exemplo. blog
ou blog.html
etc. Se houver, você precisará garantir que o MultiViews (parte de mod_negotiation) não esteja ativado. ie. %código%. Se o MultiViews estiver ativado, o Apache fará uma subrequista interna para blog.php
(por exemplo) antes que o mod_rewrite possa reescrever o URL.
Resumo
Options -Indexes -MultiViews
RewriteEngine on
# Redirect direct requests for "index.php?lang=xyz" to "/xyz/"
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{QUERY_STRING} ^lang=([a-z]{2,3})$
RewriteRule ^(index\.php)?$ /%1/? [R=301,L]
# Redirect "blog" or "ftp/<anything>" to subdomain
RewriteRule ^(blog|ftp)/?(.*)$ https://$1.czghost.czlh/$2 [R=301,L]
# Internally rewrite "/xyz/" to "/index.php?lang=xyz"
RewriteRule ^([a-z]{2,3})/$ /index.php?lang=$1 [L]