天天看點

關于Apache mod_rewrite的中文配置、使用和文法介紹(實作URL重寫和防盜鍊功能)

<b>介紹和配置:</b>

以資料庫背景驅動的動态内容的網站,經常會遇到這些的問題:

當在浏覽器的位址欄輸入一個無效的參數時,會出現資料庫的錯誤提示,這是一個安全的隐患

搜尋引擎無法收錄你的所有網頁

網頁的連結位址是一系列的參數,對浏覽使用者和搜尋引擎都不易了解

這些問題都可以通過Apache伺服器的一個基本的子產品mod_rewrite來解決,預設的安裝的Apache就會裝有這個子產品。要啟用這個子產品,打開 httpd.conf檔案,察看下面的兩行是否被屏蔽,第一行是載入mod_rewrite子產品,第二行是啟用這個子產品。

LoadModule rewrite_module modules/mod_rewrite.so AddModule mod_rewrite.c

mod_rewrite這個子產品是如何工作的呢?

mod_rewrite截獲符合特定條件的URL,并按照設定的規則将它們改寫成需要的URL。

比如,可以将 http://www.mysite.com/product.php?pid=123312 這樣的URL改寫成

http://www.mysite.com/product-123312.html 這樣的靜态URL,或者是更具體的 http://www.mysite.com/product/thinkpad-t42.html

重寫的規則

重寫的規則的表達式:

RewriteRule 模式 替換 [選項]

RewriteRule 是一個簡單的指令告訴mod_rewrite這個子產品如何去重寫,關鍵的地方在于可以在模式和替換中使用正規表達式來比對相應的字元,正規表達式的廣泛的靈活性能将動态的URL轉換成各式各樣的符合要求的靜态URL。看看這個重寫規則:

RewriteRule /products/([0-9]+) /fancy/products.php?id=$1

當你在浏覽器位址欄輸入 http://www.mysite.com/product/123 時,這個位址被重寫為 http://www.mysite.com/fancy/product.php?id=123

這樣,通路者就無法知道你的程式真正放在那個目錄,程式的真正名字是什麼,這也提高了網站的安全系數;這樣的URL也去掉了?=這些字元,易于搜尋引擎的機器人爬行你的網站。

通過正規表達式,可以寫出更複雜的重寫規則:

RewriteRule ^/products$ /content.php RewriteRule ^/products/([0-9]+)$ /content.php?id=$1 RewriteRule ^/products/([0-9]+),([ad]*),([0-9]{0,3}),([0-9]*),([0-9]*$)

重寫規則的選項有

‘forbidden’ 或 ‘f’ - 403 禁止

‘gone’ 或 ‘g’ - 410 gone

‘nocase’ 或 ‘NC’ - 大小寫敏感

‘next’/N’ - 回到第一條規則

’skip=N’ 或 ‘S=N’ - 跳過下面的N條規則

流程控制

mod_rewrite是按照從上到下的順序執行重寫的規則,如果URL比對了第一條規則,則按照第一條規則進行重寫,如果不比對,就執行第二條規則,直到最後。通過流程控制,可以定義在不同情況下采用不同的重寫規則。格式是:

RewriteCond 測試條件 Condition

這些測試條件有:

HTTP變量: HTTP_USER_AGENT, HTTP_REFERER, HTTP_COOKIE, HTTP_FORWARDED, HTTP_HOST, HTTP_PROXY_CONNECTION, HTTP_ACCEPT

連結和請求的變量: REMOTE_ADDR, REMOTE_HOST, REMOTE_USER, REMOTE_IDENT, REQUEST_METHOD, SCRIPT_FILENAME, PATH_INFO, QUERY_STRING, AUTH_TYPE

伺服器内部變量: DOCUMENT_ROOT, SERVER_ADMIN, SERVER_NAME, SERVER_ADDR, SERVER_PORT, SERVER_PROTOCOL, SERVER_SOFTWARE

系統變量: TIME_YEAR, TIME_MON, TIME_DAY, TIME_HOUR, TIME_MIN, TIME_SEC, TIME_WDAY, TIME

mod_rewrite特殊值: API_VERSION, THE_REQUEST, REQUEST_URI,

例如,利用mod_rewrite可以禁止從其他的網站連結到你的圖檔:

RewriteCond %{HTTP_REFERER} !^$ RewriteCond %{HTTP_REFERER} !^http://localhost/.*$ [OR,NC] RewriteCond %{HTTP_REFERER} !^http://mysite.com/.*$ [OR,NC] RewriteCond %{HTTP_REFERER} !^http://www.mysite.com/.*$ [OR,NC] RewriteRule .*\.(gif|GIF|jpg|JPG)$ http://mysite/p_w_picpaths/bad.gif [L,R]

<b>配置apache mod_rewrite最簡單的方法</b>:

在網上找了很多篇關于配置apache mod_rewrite的文章,發覺這篇最有用,大家需要的可參考一下。

1,通過php提供的phpinfo()函數檢視環境配置,通過Ctrl+F查找到“Loaded Modules”,其中列出了所有apache2handler已經開啟的子產品,如果裡面包括“mod_rewrite”,則已經支援,不再需要繼續設定。

如果沒有開啟“mod_rewrite”,則打開目錄 您的apache安裝目錄“/apache/conf/” 下的 httpd.conf 檔案,通過Ctrl+F查找到“LoadModule rewrite_module”,将前面的”#”号删除即可。如果沒有查找到,則到“LoadModule” 區域,在最後一行加入“LoadModule rewrite_module modules/mod_rewrite.so”(必選獨占一行),然後重新開機apache伺服器即可。

2, 讓apache伺服器支援”.htaccess”

如何讓自己的本地APACHE伺服器支援”.htaccess”呢?其實隻要簡單修改一下apache的httpd.conf設定就可以讓APACHE支 持.htaccess了。打開httpd.conf檔案(在那裡? APACHE目錄的CONF目錄裡面),用文本編輯器打開後,查找

&lt;Directory /&gt;

Options FollowSymLinks

AllowOverride None

&lt;/Directory&gt;

改為

AllowOverride All

就可以了

3,建立 “.htaccess” 檔案

如果是在windows平台下,剛開始還真不知道怎麼建立”.htaccess”檔案,因為這個檔案實際上沒有檔案名,僅僅隻有擴充名,通過普通方式是無法建立這個檔案的,别着急,馬上告訴你三種方法:

三種方法都是先建立一個htaccess.txt的文本檔案(當然,這個文本檔案的名字你可以随便取),然後有三種方式給這個檔案重命名:(1)用記事本 打開,點選檔案–另存為,在檔案名視窗輸入”.htaccess”,注意是整個綠色部分,也就是包含英文引号,然後點選儲存就行了。(2)進入cmd指令 視窗,通過cd切換當剛建立htaccess.txt檔案的檔案夾,然後輸入指令:rename htaccess.txt .htaccess ,然後點選鍵盤Enter鍵即可。(3)通過ftp連接配接htaccess.txt所在檔案夾,通過ftp軟體重命名。

那麼我們須要建立幾個“.htaccess” 檔案,裡面又輸入什麼内容呢?基本的原則是這樣,根目錄必須有一個,用于重定向(URl重寫)所有的請求都會轉到到index.php(交給前端控制 器);”./application”檔案夾下須要一個,用于拒絕所有針對該檔案夾内容的直接通路(比如 http://localhost/application/models/User.php),這樣做是因為所有通路請求必選通過前端控制器來配置設定訪 問,其次為了安全;“./library”檔案夾下的“.htaccess”同前;”./public”檔案夾下必選建一個,因為這個檔案夾的檔案全部是 供前端直接通路的,是以須要撤銷URl重寫。以下是4個“./htaccess”檔案的内容:

./.htaccess

RewriteEngine on

RewriteRule !\.(js|ico|gif|jpg|png|css)$ index.php

./application/.htaccess

deny from all

./library/.htaccess

./public

RewriteEngine off

實際上,apache的url重寫功能也可以直接在httpd.conf檔案中進行設定,這裡就不具體講了,網上相關的教程也很多。

<b>Apache的RewriteRule規則詳細介紹:</b>

R[=code](force redirect) 強制外部重定向 (rkyW z

強制在替代字元串加上http://thishost[:thisport]/字首重定向到外部的URL.如果code不指定,将用預設的302 HTTP狀态碼。 gN24M 3{C

F(force URL to be forbidden)禁用URL,傳回403HTTP狀态碼。 m&gt; 4ahue$

G(force URL to be gone) 強制URL為GONE,傳回410HTTP狀态碼。 Np'2 }6P

P(force proxy) 強制使用代理轉發。 ) Ps b&gt;'X

L(last rule) 表明目前規則是最後一條規則,停止分析以後規則的重寫。 ua 5 O Gx

N(next round) 重新從第一條規則開始運作重寫過程。 S,&lt;EEt XQ

C(chained with next rule) 與下一條規則關聯 @+ 9 &lt; O0

如果規則比對則正常處理,該标志無效,如果不比對,那麼下面所有關聯的規則都跳過。 Zs}5Smjl;%

T=MIME-type(force MIME type) 強制MIME類型 ~=KJ zOS,S

NS (used only if no internal sub-request) 隻用于不是内部子請求 /[6j)HIS

NC(no case) 不區分大小寫 ^2$ l J

QSA(query string append) 追加請求字元串 zH&gt;hx5,k'X

NE(no URI escaping of output) 不在輸出轉義特殊字元 \~ B D m

例如:RewriteRule /foo/(.*) /bar?arg=P1\%3d$1 [R,NE] 将能正确的将/foo/zoo轉換成/bar?arg=P1=zed +3a?` Z

PT(pass through to next handler) 傳遞給下一個處理 %0 #XPc("

例如: :5/Uh/ sX

RewriteRule ^/abc(.*) /def$1 [PT] # 将會交給/def規則處理 x A u/

Alias /def /ghi XyM G.r-,

S=num(skip next rule(s)) 跳過num條規則 A~Xq,BxCV

E=VAR:VAL(set environment variable) 設定環境變量

rewrite時伺服器變量: `: O\dN&gt;ON

HTTP headers:HTTP_USER_AGENT, HTTP_REFERER, HTTP_COOKIE, HTTP_HOST, HTTP_ACCEPT },5'z {3E

connection &amp; request: REMOTE_ADDR, QUERY_STRING PY3 ps2^K.

server internals: DOCUMENT_ROOT, SERVER_PORT, SERVER_PROTOCOL r}u %#G+K,

system stuff: TIME_YEAR, TIME_MON, TIME_DAY

Rewrite規則表達式的說明: #Fu&gt;|2 F|

. 比對任何單字元 wFlv i =n/

[chars] 比對字元串:chars [o c~iDx%W

[^chars] 不比對字元串:chars Lc&lt;eRVNd,

text1|text2 可選擇的字元串:text1或text2 { OT:3SS7

? 比對0到1個字元 A%Z)w z{

* 比對0到多個字元 v4 *rPG v

+ 比對1到多個字元 " o c $

^ 字元串開始标志 SKXBrD=-

$ 字元串結束标志 &amp;LQ%

\n 轉義符标志

反向引用 $N 用于 RewriteRule 中比對的變量調用(0 &lt;= N &lt;= 9) =_=*O EgO]

反向引用 %N 用于 RewriteCond 中最後一個比對的變量調用(1 &lt;= N &lt;= 9)

RewriteCond标志符 @J v# f r

'nocase|NC'(no case)忽略大小 ZCi Y,;c

'ornext|OR' (or next condition)邏輯或,可以同時比對多個RewriteCond條件

RewriteRule适用的标志符 hLuJ WjCV

'redirect|R [=code]' (force redirect)強迫重寫為基于http開頭的外部轉向(注意URL的變化) 如:[R=301,L] uC[d%v`

'forbidden|F' (force URL to be forbidden)重寫為禁止通路 2F T-}w 0;

'proxy|P' (force proxy)重寫為通過代理通路的http路徑 F(0Z ] # +

'last|L' (last rule)最後的重寫規則标志,如果比對,不再執行以後的規則 ?%;B`2 nDR

'next|N' (next round)循環同一個規則,直到不能滿足比對 ,4yG(O $ )

'chain|C' (chained with next rule)如果比對該規則,則繼續下面的有Chain标志的規則。 p_gA/ . v=

'type|T=MIME-type' (force MIME type)指定MIME類型 1^tSn #j

'nosubreq|NS' (used only if no internal sub-request)如果是内部子請求則跳過 LhZZ c`|7t

'nocase|NC' (no case)忽略大小 b.@ H1 L

'qsappend|QSA' (query string append)附加查詢字元串 *b: u * `@

'noescape|NE' (no URI escaping of output)禁止URL中的字元自動轉義成%[0-9]+的形式。 ~ t"n%SgY

'passthrough|PT' (pass through to next handler)将重寫結果運用于mod_alias IL2 e6 b

'skip|S=num' (skip next rule(s))跳過下面幾個規則 loR,X W7 z

'env|E=VAR:VAL' (set environment variable)添加環境變量

實際操作

例子: "IOC[ #&amp;G

RewriteEngine on !?S5IG LOj

RewriteCond %{HTTP_USER_AGENT} ^MSIE [NC,OR] _R N/7\

RewriteCond %{HTTP_USER_AGENT} ^Opera [NC] !&amp;' # a

RewriteRule ^.* - [F,L] 這裡”-”表示沒有替換,浏覽器為IE和Opera的訪客将被禁止通路。

例子: *U( 1iv0 n

RewriteEngine On QWU5-p9e 8

RewriteBase /test Q3 K ;kS

RewriteCond %{REQUEST_FILENAME}.php -f rU/-Wq` B

RewriteRule ([^/]+)$ /test/$1.php ?7r mw y\

#for example: /test/admin =&gt; /test/admin.php I v 80,hW

RewriteRule ([^/]+)\.html$ /test/$1.php [L] aufcd57

#for example: /test/admin.html =&gt; /test/admin.php

限制目錄隻能顯示圖檔 yKX: Z4I/

&lt; IfModule mod_rewrite.c&gt; + #i ,87

RewriteEngine on L @ ^ !(

RewriteCond %{REQUEST_FILENAME} !^.*\.(gif|jpg|jpeg|png|swf)$ mtHi9).,y|

RewriteRule .*$ - [F,L] [ 3bwbfHhi

&lt; /IfModule&gt;