URL重定向是.htaccess的重頭戲,它能夠將長地址轉爲短地址、將動態地址轉爲靜態地址、重定向丟失的頁面、防止盜鏈、實現自動語言轉換等。筆者以爲難點是在正則表達式的運用和理解上。有關htaccess的正則表達式用法,請查閱《.htaccess正則表達式》一文。 php
實現全部這些神奇功能的模塊叫作mod_rewrite,請確保你的服務器安裝並啓用了該模塊:css
sudo a2enmod rewrite
咱們通常會把全部涉及URL重寫或者重定向的代碼這樣放置:html
<IfModule mod_rewrite.c> # Turn on rewrite engine Options +FollowSymlinks RewriteEngine on # More rules below ... </IfModule>
一些咱們須要注意的地方:正則表達式
下面咱們開始講解一些例子。數組
Options +FollowSymlinks
RewriteEngine on
RewriteRule ^(.*)\.htm$ $1.php [NC]
注意事項:瀏覽器
RewriteEngine on RewriteBase / RewriteRule ^(.*)\.htm$ $1.php [R,NC,L]
注意事項:安全
在討論R=302臨時重定向後,理解R=301永久重定向也就容易多了:服務器
RewriteEngine on RewriteRule ^(.*)$ http://newdomain.com/$1 [R=301,NC,L]
利用URL重寫,咱們能夠很方便地實現長短地址的轉換,可是用重定向就不合適了。網絡
RewriteEngine On RewriteRule ^grab /public/files/download/download.php
若訪問
http://mysite/grab?file=my.zip
則會執行該頁面:
http://mysite/public/files/download/download.php?file=my.zipapp
Options +FollowSymlinks RewriteEngine on RewriteCond %{HTTP_HOST} ^www\.(.*) [NC] RewriteRule ^(.*)$ http://%1/$1 [R=301,NC,L]
RewriteEngine On RewriteCond %{HTTP_HOST} ^(.*)$ RewriteRule (.*) http://www\.%1/$1 [R=301,L]
若是你不湊巧買到了不支持多域名的主機,那麼.htaccess或許能夠幫助你。如今假設你有域名domain-one.com和domain-two.com,而且在服務器根目錄有對應文件夾one和two,那麼經過下面的改寫就能讓Apache同時接受者兩個域名的請求:
#two domains served from one root.. RewriteCond %{HTTP_HOST} domain-one.com RewriteCond %{REQUEST_URI} !^/one RewriteRule ^(.*)$ /one/$1 [L] RewriteCond %{HTTP_HOST} domain-two.com RewriteCond %{REQUEST_URI} !^/two RewriteRule ^(.*)$ /two/$1 [L]
查詢字符串是指URL請求中「問號」後面的部分。好比,http://mysite/grab?foo=bar中粗體部分就是查詢字符串,其中變量名是foo,值是bar。
QSA標誌( Query String Appending)用於在URI中截取查詢字符串,這個截取操做是經過小括號正則表達式實現的:
RewriteEngine On
RewriteRule /pages/(.+) /page.php?page=$1 [QSA]
經過QSA,咱們能夠將簡單連接/simple/flat/link/ 映射成 server-side.php?first-var=flat&second-var=link
RewriteEngine On RewriteRule ^/([^/]+)/([^/]+)/? /index.php?first-var=$1&second-var=$2 [QSA]
RewriteEngine On RewriteCond %{QUERY_STRING} foo=(.*) RewriteRule ^grab(.*) /page.php?bar=%1
RewriteEngine On RewriteCond %{QUERY_STRING} foo=(.+) RewriteRule ^grab/(.*) /%1/index.php?file=$1 [QSA]
只需在要開始剝離的連接後面加個「問號」,而且不要啓用QSA標誌,就可剝離查詢字符串
RewriteEngine On # Whatever QS is RewriteCond %{QUERY_STRING} . # I don't want it with Question mark RewriteRule foo.php(.*) /foo.php? [L]
咱們在第一篇.htaccess基礎中提到了不少有用的訪問控制方法,其實經過Rewrite也能實現相似的功能,並且能夠更強大!
以前利用Order、Files及FilesMatch命令實現的訪問控制能夠知足大部分要求,可是當用戶被拒絕時,他們看到的是碩大的「403 Forbidden」,若是你不想傷害用戶的感情,就須要顯示一些別的東西,經過Rewrite就能夠實現這個特性:
RewriteEngine On RewriteCond %{REQUEST_FILENAME} !^(.+)\.css$ RewriteCond %{REQUEST_FILENAME} !^(.+)\.js$ RewriteCond %{REQUEST_FILENAME} !special.zip$ RewriteRule ^(.+)$ /chat/ [NC]
RewriteEngine On RewriteCond %{REQUEST_FILENAME} !([^/]+)\.css$ RewriteCond %{REQUEST_FILENAME} !([^/]+)\.js$ RewriteRule ^(.+)$ /chat/ [NC]
什麼是User-agent?User-agent用於瀏覽器向服務器「自報家門」,更確切的說是全部HTTP客戶端都得用User-agent向服務器「自報家門」,以便服務器對不一樣的客戶端做出不一樣響應。好比,某站點可能須要對瀏覽器、搜索引擎crawl還有各種下載工具做出不一樣的響應。服務器就是經過所謂的User-agent進行區分的。
若是你的服務器提供某些資源的下載,那麼你就必須多加當心諸如「迅雷」等下載軟件,由於它們可能把你網站資源吸乾,而且影響你的正常訪客訪問。爲此,咱們能夠利用Rewrite限制某些UA的訪問:
RewriteEngine on RewriteCond %{HTTP_USER_AGENT} 2.0.50727 [NC] RewriteRule . abuse.txt [L]
一般,咱們不會僅限制一個UA。利用[OR]便可實現對多個UA做出統一處理:
RewriteEngine on RewriteCond %{HTTP_USER_AGENT} 2.0.50727 [NC,OR] RewriteCond %{HTTP_USER_AGENT} ^BlackWidow [NC,OR] # etc.. RewriteCond %{HTTP_USER_AGENT} ^Net\ Vampire [NC] RewriteRule . abuse.txt [L]
盜鏈,特別是圖片,是很是可恥的!哪怕將圖片複製到本身服務器上,也比盜用他人的圖片連接來得光彩!(吐糟完畢)
.htaccess的Rewrite功能能夠提供很是簡單、有效的方法阻止這種可恥行爲:
RewriteEngine On RewriteCond %{HTTP_REFERER} !^$ RewriteCond %{HTTP_REFERER} !^http://(www\.)?lesca\.me/ [NC] RewriteCond %{REQUEST_URI} !hotlink\.png [NC] RewriteRule .*\.(gif|jpg|png)$ /hotlink.png [NC]
簡單解釋一下該規則的功能: