Dot-Htaccess

多個條件重定向都在一個 .htaccess(登陸頁面)中

  • September 7, 2021

我有一個只有“即將推出”單頁 html 的文件夾。

然後我有幾個域,我會根據需要不時指向這個文件夾。

簡單吧?

那麼我想要的是一個條件,如果原始請求的頁面是非 www 去 www(301> 加上如果不是 https 去 https(301)然後將所有流量重定向到https://www.originating-domain.xzy/index.html(302)

目的是成為一個多用途的登錄頁面,但總是 301 到https://www 然後 302 到index.html

我已經在每個站點上都有這個非 www 到 www 和 http 到 https 工作:

RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteRule ^ https://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [L,R=301]

現在我想將 302 臨時重定向添加到index.html.

還是有更好的方法來完全做到這一點?就像因為無論如何這都是暫時的…… 302所有流量到索引我試過這個但沒有奏效

RewriteCond %{REQUEST_URI} !.*index\.html
RewriteRule https://www.%{HTTP_HOST}/index.html [R=302,L]
RewriteCond %{REQUEST_URI} !.*index\.html
RewriteRule https://www.%{HTTP_HOST}/index.html [R=302,L]

這有幾個問題……

  1. 您似乎完全缺少RewriteRule 模式(第一個參數),因此該指令將無法匹配。
  2. 如果這確實匹配,它將再次www.為子域添加前綴。我假設您將此重定向放在規範重定向(HTTP 到 HTTPS 和非 www 到 www)之後 - 正如您應該做的那樣。因此,這將重定向到,因為在觸發此重定向時,主機名已經是規範的。https://www.www.example.com/index.html

條件(指令)並不是真正需要的RewriteCond,因為該檢查(/index.html尚未請求)可以由RewriteRule指令本身更有效地處理。

例如:

RewriteRule !^index\.html$ /index.html [R=302,L]

無需在替換字元串中包含方案+主機名,因為無論如何您都希望重定向到相同的內容。如果你想明確一點,你可以寫https://%{HTTP_HOST}/index.html.

請注意,就目前而言,index.html不能引用任何其他本地資源(圖像、CSS、JavaScript 等),因為這些請求也會被重定向。要允許訪問本地資源,您需要添加幾個條件來排除對靜態資源的請求。

RewriteCond %{REQUEST_URI} !.\.(jpg|png|webp|css|js)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule !^index\.html$ /index.html [R=302,L]

或者,將這些資源託管在外部域上。(或在子目錄中並排除整個子目錄。)

但是,如果完全選擇“重定向”,我可能會重定向到一個更獨特/更有意義的命名文件,例如。/coming-soon.html. 使用的問題/index.html是,如果您以後想在該 URL 上提供不同的內容並且它已被記憶體(無論出於何種原因)。雖然/coming-soon.html可能應該是“noindex”。

但是,最好根本不重定向,而是提供臨時的“503 服務不可用”響應。有關更多資訊,請參閱在網站管理員堆棧上對以下問題的回答:


在旁邊:

RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [L,R=301]

您是否在管理 SSL 連接的前端代理後面?

如果你是,那沒關係,儘管檢查HTTPS伺服器變數的第二個條件因此是多餘的。但是,如果您不在X-Forwarded-Proto: httpsSSL 代理後面,那麼如果將標頭注入請求中,則這些指令很容易被規避(即,使用者不會被重定向到 HTTPS) 。


更新:

好的,這可以按我的意願工作。但是我可以以某種方式將它們結合起來嗎?

RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteRule ^ https://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

RewriteCond %{REQUEST_URI} !.*coming-soon\.html [NC]
RewriteRule ^(.*)$ https://%{HTTP_HOST}/coming-soon.html [R=302,L]

如上所述,最後一條規則與以下規則基本相同(當與前面的規範重定向結合使用時),它更簡單、更有效:

RewriteRule !^coming-soon\.html$ /coming-soon.html [R=302,L]

在第二條規則中,您還應該將RewriteRule 模式從更改^(.*)$^(與第一條規則相同)。^(.*)$不必要地擷取反向引用並且效率較低。

您在之前的評論(現已刪除)中提到您希望它也適用於任何子域。它對任何子域都“有效”,但是,它總是會預先添加一個額外的www子域,這可能是可取的,也可能不是可取的?www(在子域上擁有子域並不常見。YMMV。)

沒有真正需要“組合”這些規則。如果您想在 302 重定向到“即將推出”頁面之前 301 重定向到 www+HTTPS,那麼您當然不能將它們組合起來。雖然前兩條規則(301 重定向)可以“組合”成一條規則,但它沒有任何作用。

這裡唯一的小問題是可能(最多)2個重定向。首先,原始 URL 路徑上的 www+HTTPS 的 301 和第二個 302 到“即將推出”頁面。

當您將使用者重定向到臨時“即將推出”頁面時,我會質疑您是否真的需要最初的 301 重定向到 www+HTTPS。一旦您實施了新網站(替換“即將推出”頁面),您將實施規範重定向。302重定向仍然可以重定向到www+HTTPS。(但是,/coming-soon.html直接請求時存在邊緣情況。)

例如:

# 302 redirect to the coming soon page (www+HTTPS)
RewriteCond %{HTTP_HOST} ^(?:www\.)?(.+?)\.?$
RewriteRule !^coming-soon\.html$ https://www.%1/coming-soon.html [R=302,L]

# Edge case...
# The following two rules only apply if "/coming-soon.html" is requested directly
# and either non-www hostname and/or HTTP is requested
# in which case 301 redirect to the same on www+HTTPS

# www subdomain is missing...
RewriteCond %{HTTP_HOST} !^www\.
RewriteRule ^ https://www.%{HTTP_HOST}%{REQUEST_URI} [R=301,L]

# HTTP + www has been requested
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [R=301,L]

任何請求http://example.com/foo都是 302 直接重定向到https://www.example.com/coming-soon.html.

如果http://example.com/coming-soon.html應該被請求那麼它是 301 重定向到https://www.example.com/coming-soon.html(只是修復 HTTPS 和 www 子域)。

最多只有 1 個外部重定向。

引用自:https://serverfault.com/questions/1076324