簡體   English   中英

如何為 Apache 編寫 .htaccess 文件以附加 PHP(如果未提供)並使用編寫良好的 404 頁面

[英]How can I write an .htaccess file for Apache to append PHP (if not supplied) AND use a well-written 404 page

在 Apache 中,我有一個有效的 .htaccess 文件,它將 .php 擴展名附加到請求的網站頁面,例如:https://{{domain}}/sales -> 提供來自 https://{{ domain}}/sales.php 而對訪問者來說它看起來像 https://{{domain}}/sales

它完美無缺地工作。

但是,我無法解決如何還使用來自服務器的精美 404.php 頁面。

這是我當前的 .htaccess 文件內容:

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^([^\.]+)$ $1\.php [NC,L]

證據:如果我關閉我的 .htaccess 文件(重命名),404 頁面會根據我的 httpd.conf 設置運行良好。 所以,我幾乎肯定是這個不成熟的 .htaccess 文件阻止了我在找不到 sales.php 頁面時提供花哨的 404 頁面。

httpd.conf 中的確切行是什么:

DocumentRoot "/var/www/html/"
ErrorDocument 404 "/404.php"

此外,我已經嘗試了每一個:(並在之后重新加載了 httpd)

ErrorDocument 404 "/var/www/html/{{virtualHostDir}}/404.php"
ErrorDocument 404 "/404.php"
ErrorDocument 404 "404.php"

我什至嘗試將 ErrorDocument 直接添加到 virtualHost 設置中,但無濟於事。


當您收到 404 並且 .htaccess 文件就位時,實際會發生什么?

我得到一個沒有 html 的頁面,它只是說,“找不到文件。”

DocumentRoot "/var/www/html/" ErrorDocument 404 "/404.php"

那看起來是正確的。 如果 404 錯誤文檔位於/var/www/html/404.php則沒有明顯的原因(根據給定的信息)為什么這不能按預期工作。 它似乎不是.htaccess文件的內容 - 盡管您可以嘗試另一種方法(見下文)。

提供給ErrorDocument指令的路徑應該是一個相對於文檔根目錄的 URL 路徑——以斜杠開頭。 (為了觸發對相應錯誤文檔的內部子請求。)

我什至嘗試將 ErrorDocument 直接添加到 virtualHost 設置

但是,如果您使用的是 VirtualHost 容器,那么這些設置實際上應該在相應的 vHost(s) 中。 vHost 中的任何內容都將覆蓋主服務器配置。

顯然,如果您對服務器配置/虛擬主機進行任何更改,則需要重新啟動 Apache。

由於您無論如何都在使用.htaccess ,您還可以在.htaccess設置ErrorDocument - 這將反過來覆蓋虛擬主機/服務器配置。

 RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule ^([^\\.]+)$ $1\\.php [NC,L]

這沒有什么特別的錯誤......您正在匹配一個不包含點的請求 URL 路徑,並且提供它尚未映射到文件或目錄,您正在附加一個.php擴展名。

只是關於此的一些注意事項:

  • 無論“帶有.php擴展名”的.php實際存在,您都會附加.php擴展名。 這不一定是錯誤的,只是然后在/does-not-exist.php而不是/does-not-exist上觸發了 404。 您可以改為檢查目標文件是否存在。 這將避免必須檢查請求是否尚未映射到文件或目錄。

  • 檢查請求未映射到文件的第一個條件可能是不必要的,除非您的文件沒有文件擴展名(我認為不太可能)。

  • [^\\.] - 不需要反斜杠轉義正則表達式字符類中的文字點。 (盡管這樣做沒有壞處,但 IMO 的可讀性除外。)

  • $1\\.php - 無需反斜杠轉義RewriteRule替換中的文字點。 這個參數是一個“普通”字符串(不是正則表達式),這里的點沒有特殊意義。 (雖然,再一次,這樣做沒有壞處,除了可讀性。)

  • 此處不需要RewriteRule上的NC標志,因為您正在匹配除正則表達式中的一個點之外的所有內容,無論如何,它自然包括大寫和小寫字母。

  • 如果這就是您使用 mod_rewrite 的全部內容,那么您可以改用 MultiViews 來處理您的無擴展 URL。 這就是 MultiViews(mod_negotiation 的一部分)所做的。 給定對/path/to/foo的請求,如果/path/to/foo.php存在, mod_negotiation 將提供該文件。 您需要刪除現有的 mod_rewrite 指令(因為它們會有效地發生沖突並且無論如何都會被忽略),然后在.htaccess文件的頂部啟用 MultiViews:

     Options +MultiViews

或者,考慮到我上面提出的幾點,請嘗試以下操作:

RewriteEngine On

RewriteCond %{DOCUMENT_ROOT}/$1.php -f
RewriteRule ^([^.]+)$ $1.php [L]

注意:我假設您的.htaccess文件位於文檔根目錄中,即。 /var/www/html/.htaccess

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM