Wordpress

WordPress 固定連結 404 怎麼修?3 步驟排查

網站搬完新主機、或是網域剛換好,你登入後台檢查,首頁正常打開,才剛鬆一口氣——點進任何一篇文章、任何一個分類頁,畫面卻清一色跳出 404 Not Found。文章明明沒被刪除,後台清單裡都還找得到,偏偏前台就是連不上,把幾篇文章輪流點過一次,結果都一樣。

這種整站性的 404,通常不是內容真的不見了,而是 WordPress 固定連結(永久連結)的網址重寫規則沒有正確寫回伺服器。跟單篇文章網址打錯字、或某一篇內容被刪除這種個別的 404 不一樣,這裡要處理的是整批同時壞掉的情況,只要重寫規則沒吃進伺服器,不管資料庫裡有沒有這篇文章,前台一律進不去。

先從固定連結背後怎麼運作講起,再一路拆到你手邊環境該怎麼查、怎麼修。

網址結構看起來沒錯,為什麼還是跳出 404?

第一步不是急著改設定,是先確認問題出在哪一層。WordPress 剛安裝好的預設狀態,其實不會用/年份/月份/文章名稱/這種好看網址,而是用查詢字串,像?p=123這樣的寫法,直接把文章 ID 帶給伺服器去找對應內容。後台「設定」裡的「固定連結」,做的事只是把這串查詢字串包裝成人類看得懂的網址,內容本身有沒有這篇文章,跟這層包裝完全是兩回事。

問題在於,這層包裝不是 WordPress 自己就能生效,它需要伺服器端有一組網址重寫規則接手,把訪客看到的/slug/這種乾淨網址,在背後導回index.php去處理,伺服器才知道該把這個網址對應到哪一篇文章。Apache 環境靠的是mod_rewrite模組,Nginx 環境則要靠try_files這類指令。這條規則一旦不見或失效,伺服器收到/slug/這種請求時,不會知道要導去index.php,而是照字面去找一個真的叫做 slug 的資料夾或檔案,當然找不到,只好回傳 404。這跟 WordPress 資料庫裡有沒有這篇文章,完全是兩件事。

重寫規則存在時請求會導回 index.php 正常顯示,規則不見時伺服器照字面找不到檔案就回傳 404
有沒有重寫規則決定兩種結局:有就導回 index.php 對應到文章,沒有就照字面找不到檔案、整站撞成 404。

自己就能驗證的方法很簡單,把網址結構暫時切回最原始的「一般」格式,用?p=123這種帶 ID 的網址去開同一篇內容。如果能正常打開,代表內容還在、資料庫沒問題,問題出在重寫規則沒有正確寫回伺服器;如果連這種最原始的網址都打不開,才要往內容本身或資料庫方向去查。

固定連結為什麼會整站壞掉?

固定連結會整站壞掉,通常脫離不了下面四種情境,你可以先挑最像自己踩到的那一種看,四個原因彼此獨立,不用照順序讀完。

固定連結整站 404 的四個常見原因:搬新主機沒寫入規則、.htaccess 被覆寫、Nginx 不自動產生、外掛規則衝突
固定連結整站壞掉通常逃不出這四種情境,四個原因彼此獨立,先挑最像自己踩到的那一種對照。

原因一:搬新主機或換網域後,新環境沒有寫入對應的重寫規則

換主機商、搬到新的網域,是最常見的踩雷情境。固定連結的重寫規則,原本是寫在舊伺服器的設定檔裡,像 Apache 的.htaccess,或存在 WordPress 資料庫的規則快取裡,搬到新環境時,這份設定不一定會被完整帶過去。新主機說不定還換了不同的網站伺服器軟體,例如從 Apache 換成 Nginx,固定連結在新環境裡可能從一開始就沒有被正確產生過,不是壞掉,而是根本沒建立起來。

原因二:.htaccess 被外掛、佈景主題或手動編輯覆寫

.htaccess是 Apache 環境下,WordPress 用來寫入重寫規則的檔案,問題是它太容易被動到。安全性外掛、快取外掛、佈景主題安裝流程,都可能自動修改這個檔案;如果是自己或工程師手動編輯過,也可能不小心刪掉 WordPress 負責的那一段區塊,或打錯語法,導致整段規則失效,甚至整個檔案直接消失。

原因三:Nginx 環境本來就不會自動產生固定連結規則

這是台灣中文教學最常漏講的一塊。Nginx 沒有 Apache 那種目錄層級可寫入的設定檔,也就是沒有.htaccess這回事,WordPress 本身也沒有權限去改 Nginx 的伺服器層設定。WordPress 官方文件講得很直接,Nginx 沒有.htaccess那類機制,WordPress 也沒辦法幫你自動修改伺服器設定,自然沒辦法幫你產生重寫規則。

固定連結的規則,在 Nginx 環境下一定要由管理者手動寫進設定檔,不會因為你在後台按下「儲存」就自動生效。愈來愈多主機商把預設環境換成 Nginx,或是用 Nginx 反向代理搭配 Apache 的混合架構,讀者未必知道自己踩到的是哪一種。

原因四:外掛或自訂文章類型註冊的規則彼此衝突

會員系統、電商、自訂文章類型,像作品集頁、活動頁,這類外掛通常會在啟用時「順便」向 WordPress 註冊自己的一套網址規則。WordPress 有一個叫WP_Rewrite的核心機制,專門負責管理這些規則,外掛開發者可以透過它自訂新的規則、或增加新的網址端點。麻煩的是,如果兩個外掛剛好註冊了相近甚至衝突的網址結構,或是某個外掛更新後沒有正確重新註冊規則,就可能讓特定分類、特定文章類型整批變成 404,其他一般文章卻還是正常。

放著 404 不管,網站會流失什麼?

放著不管前,先想清楚代價是什麼,才知道這件事該排多前面處理。Google 官方部落格曾公開說明過,網站上偶爾出現幾個 404,本身不會拖累網站其他網址在搜尋結果裡的表現,這是網路正常的一部分,不是什麼扣分紀錄。但這裡要處理的整站性 404 是另一回事,原本正常被收錄、有排名、甚至有外部網站連過來的重要頁面,一次全部變成 404,跟本來就偶爾幾個網址失效,完全不是同一個等級的問題。

對讀者來說,最直接的是點進連結卻進不去的挫折,原本想看的內容找不到,信任感會被打折扣。對搜尋引擎與外部連結來說,只要頁面持續回傳 404,原本指向這些頁面的外部連結會變成死連結,而累積在這些頁面上的搜尋能見度,也會隨著頁面陸續被搜尋引擎從索引中排除而慢慢流失,不是網站一恢復正常就能立刻補回來的。

另外有一點容易被忽略,如果網站設定了自訂錯誤頁,畫面上看起來像正常的 404 提示,但伺服器實際回傳的狀態碼卻不是 404,等於變成所謂的 soft 404,對搜尋引擎理解網站反而更不利,它會誤以為這個網址是一個正常、有效的頁面,持續花資源去檢視一個其實不存在的內容。修復固定連結的同時,也順手確認自訂錯誤頁有沒有正確回傳 404 狀態碼。

修法一:重新儲存永久連結設定

多數整站性 404,第一步不用碰任何設定檔,先登入 WordPress 後台,進入「設定」裡的「永久連結」頁面,不用更動任何結構選項,直接按下「儲存變更」就好。

在永久連結設定頁不改任何結構選項,直接按最底部的儲存把重寫規則重新寫回伺服器
進到設定→永久連結,不用動任何結構選項,按一次最底部的儲存,就會強迫 WordPress 重新產生並寫回整套重寫規則。

這個動作背後在做的事,比看起來重要得多。WordPress 會重新產生整套網址重寫規則,把舊的規則快取清掉,再重新寫回伺服器;如果你的環境是 Apache,這一步還會連帶把新的規則寫回.htaccess檔案。很多時候固定連結會壞掉,只是因為這套規則沒有被正確產生或寫入,重新存一次永久連結設定,等於強迫 WordPress 重新做這件事,一次就解決大半案例。

如果你連後台都連不上,也不代表束手無策。試著直接在網址列輸入/wp-login.php這個固定路徑登入,後台登入頁走的是實體檔案,不是固定連結規則,通常不會受重寫規則失效影響;先用這條路徑登進後台,再回頭處理永久連結設定。

修法二:檢查伺服器端的重寫規則本身

如果重新儲存永久連結,問題還是沒解決,代表癥結不在 WordPress 這一層,而是伺服器根本沒有把規則吃進去。接下來要分 Apache 與 Nginx 兩條路徑分別檢查,這也是整篇技術含量最高的一段,對照你自己的主機環境往下讀就好。

Apache 靠 .htaccess 能在後台按儲存自動寫回規則,Nginx 沒有 .htaccess 一定要管理者手動加 try_files
同一組重寫規則,Apache 按儲存就自動寫回,Nginx 卻得管理者手動加 try_files,所以在 Nginx 按重存不會有反應。

用 Apache 的網站,先確認 .htaccess 有沒有跟著壞掉

第一件事,是確認網站根目錄底下真的有.htaccess這個檔案。有些主機控制台預設把這類以點開頭的檔案隱藏起來,得先在檔案總管裡另外開啟顯示隱藏檔案才看得到,別急著下結論說檔案不見了。

找到檔案之後,把內容拿去跟 WordPress 官方文件列出的標準版本核對。正確版本大致長這樣:

# BEGIN WordPress
RewriteEngine On
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
# END WordPressCode language: plaintext (plaintext)

看你的檔案裡,這段 WordPress 負責的區塊有沒有被整段清空,或是中間某一行語法被打斷、漏字。如果這段完整比對起來沒問題,問題可能出在檔案權限,權限設得太嚴格,WordPress 本身沒辦法自動寫入或修復這個檔案,這種情況通常要請主機商協助調整權限。

還有兩項屬於伺服器層級的設定,一般使用虛擬主機的人自己是看不到、也改不了的:伺服器有沒有啟用mod_rewrite模組、以及該目錄的AllowOverride設定,有沒有允許.htaccess裡的規則生效。這兩項只能透過主機商後台或客服確認,如果前面幾項都核對過還是不對,下一步就該往這裡問。

用 Nginx 的網站,「重新儲存」這步為什麼沒用?

前面重新儲存永久連結這一步,在 Nginx 環境下其實不會產生任何實際效果,這也是為什麼很多讀者明明照著網路教學按過儲存,404 還是原封不動。

原因跟前面提到的一樣,Nginx 沒有目錄層級可寫入的設定檔,也就是沒有.htaccess這回事,WordPress 本身也沒有權限去改 Nginx 的伺服器層設定,自然沒辦法幫你把規則寫進去。

正確做法,是在 Nginx 的server設定區塊裡,手動加入一段規則,把不是實體檔案、也不是實體資料夾的請求,導去index.php並帶上查詢字串,例如:

location / {
    try_files $uri $uri/ /index.php?$args;
}Code language: Nginx (nginx)

如果你不是自己管理伺服器,而是用代管主機、或是有工程師負責維護,這一步要請對方協助加入或確認設定;如果網站是安裝在子目錄底下,對應的規則路徑也要跟著調整,不能整段照抄。剛從 Apache 主機搬到 Nginx 主機,或是搬到用 Nginx 反向代理的雲端主機,最容易踩到這個差異。建議對照前面原因三提到的情況,先確認自己的主機環境是哪一種。

修法三:排查外掛與佈景主題的規則衝突

前面兩步都做完,伺服器端的重寫規則也確認正常,卻還是有頁面 404,通常代表問題出在外掛或佈景主題彼此的規則衝突,而不是伺服器設定本身。這時候不必憑感覺一個一個猜,系統化排查會快得多。

先把所有外掛一次整批停用,看 404 是不是就此消失。如果消失了,再一個一個重新啟用,每啟用一個就實際測試一次剛才壞掉的網址,抓出真正造成衝突的那一個。同樣的邏輯也適用在佈景主題,先切回 WordPress 內建的預設佈景測試,確認問題是不是出在自訂佈景上。

有一類外掛特別要注意:凡是牽涉到自訂文章類型或自訂分類的外掛,像會員系統、電商、作品集頁,通常在啟用、停用、更新之後,都需要重新整理一次永久連結設定才會生效。如果已經重新整理過,問題還是沒解決,就要考慮是不是兩個外掛剛好註冊了相近或衝突的網址結構,彼此蓋掉對方。

想再深入一點的讀者,還有一條比較進階的路徑,透過檢視實際生效中的重寫規則陣列,直接查看 WordPress 目前套用了哪些規則,而不是只能用猜測加重新整理這種方式一次次去試。WordPress.org 官方外掛目錄裡的 Rewrite Rules Inspector 就是為這件事而生,它能列出所有生效中的規則、也能拿一個網址去測試看看它會對應到哪一條規則,對排查外掛衝突特別有幫助。

三個修法都做完仍是 404,該找誰幫忙?

前面三個修法都試過,404 還是沒解決,多半代表問題已經不在你自己能碰的層級,而是伺服器本身的設定。可能是主機根本沒有啟用網址重寫功能、前面架了一層反向代理或 CDN 把請求攔在中間、又或者是資安規則把看起來乾淨的網址誤判成攻擊行為直接擋下來,這些都只有主機商或工程師有權限處理,自己在後台再怎麼點也點不出結果。

去找主機商或工程師之前,先把排查資訊準備齊全,能大幅縮短對方診斷的時間。至少要能回答這幾件事:網站用的是 Apache 還是 Nginx,前面幾節應該已經幫你確認過;目前.htaccess的內容、或 Nginx 對應的設定片段;實際會出現 404 的網址範例,最好準備兩三個;瀏覽器或伺服器記錄裡,看到的確切錯誤訊息是什麼。

這也呼應前面提到,愈來愈多主機商把預設環境換成 Nginx,或是用 Nginx 做反向代理的混合架構。不確定自己的主機屬於哪一種、有沒有權限自己動手改,與其自己憑感覺調整設定,不如直接把上面這些資訊準備好,問主機商最快。

整站性的 404,核心問題幾乎都出在同一個地方,固定連結的重寫規則沒有正確寫回伺服器,不是內容真的不見了。多數情況,只要照著這個順序做,自己就能把網站救回來:先重新儲存一次永久連結設定,沒有用的話,再檢查伺服器端的重寫規則,分 Apache 與 Nginx 兩條路徑分別排查;還是不行,就往外掛與佈景主題的規則衝突去找。真的走到需要動主機設定、或牽涉到伺服器權限的部分,不必自己瞎猜著改設定檔,直接交給有權限的主機商或工程師處理就好。

資料來源
  1. Apache HTTPD / .htaccess – Advanced Administration Handbook — WordPress
  2. Nginx – Advanced Administration Handbook — WordPress
  3. Do 404 errors hurt my site? — Google