apache .htaccess 僞靜態重定向,防盜鏈 限制下載...

301全站跳轉php

RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.old\.net$ [NC]
RewriteRule ^(.*)$ http://www.new\.net/$1 [L,R=301,NC]css

其中 http://不能省略,否則出現絕對路徑加在跳轉重寫前面的html

.htaccess 正則表達式
# 位行首表示註釋
[F] Forbidden (禁止):
    命令服務器返回403 Forbiden 錯誤給用戶瀏覽器

[L] Last rule (最後一條規則)
    告訴服務器在本條規則執行完後中止重寫URL

[N] Next (下一條規則)
    告訴服務器繼續重寫,指導全部重寫指令都執行過

[G] Gone (丟失)
    命令服務器返回410 GONE(no longer exists)錯誤消息

[P] Proxy (代理)
    告訴服務器經過mod_proxy模塊處理用戶請求

[C] Chain (捆綁)
    告訴服務器將當前的規則和前面的規則進行捆綁

[R] Redirect(重定向)
    告訴服務器發出重定向消息,以便用戶瀏覽器發出rewitten/modified(重寫/修改) 請求

[NC] No Case(不區分大小寫)
    對客戶端請求的URL不區分大小寫

[PT] Pass Through(放行)
    讓mod_rewrite 模塊將重寫的URL傳回給Apache作進一步處理

[OR] Or(邏輯或)
    用邏輯「或」將兩個表達式鏈接在一塊兒,若是結果爲「真」,則會應用後繼的相關規定

[NE] No Escape (禁止轉義)
    命令服務器在輸出時禁用轉義字符

[NS] No Subrequest(禁用子請求)
    若是存在內部請求,則跳過當前命令

[QSA] Append Query String(追加查詢字符串)
    命令服務器在URL末尾追加查詢字符串

[S=x] Skip(跳過)
    若是知足某指定條件,則跳事後面第X條規則

[E = Variable:value](環境變量)
    命令服務器交將值 value賦給變量 variable

[T=MIME-type] Mime Type (MIME 類型)
    聲明目標資源所屬的MIME類型

[]
  匹配一個字符集,如[xyz]能夠匹配x,y或者z

[^]
   如:[xyz]+ 會以任何順序,次數匹配x,y,z的出現

[a-z]
    連字符(-)表示匹配從字母a到z的全部字符串

a{n}
    指定字母a出現的次數爲N次,知足該條件時匹配。如x{3}僅與xxx匹配

a{n,}
    指定字母a出現的次數至少爲N次,例如X{3}能夠與XXX或者xxxxx等級匹配

a{n,m}
    指定a出現的次數至少爲n到m次    

()
  用於將正則表達式分組,知足第一組正則表達式的字符串會被存儲在變量$1中,以此類推。若是括號呈的不是正則表達式,例如(myname)?press 將可以匹配有或者沒有myname前綴的press

^
 位於行首。注意:和中括號中的[^]意義不一樣

$
 位於行末

?
  例如 world?會匹配world或者worldx,而如 wor(ld)? 會匹配wor或者world,又如:x?會匹配「空字符」或者一個x

!
  邏輯非。例如:"!myname"將會匹配除了「myname」之外的全部字符串

.
 表示任意字符

-
 命令apache「不要」重寫URL,例如:"xxx.domian.com.* -[F]"

+
 匹配至少一個任意字符,例如:G+ 匹配以G開頭,而且後面至少有一個字符的字符串

*
 匹配零個或多個字符,例如:「。」匹配任意字符

|
  邏輯「或」。與[OR]不一樣的是,它是匹配字符串,例如(x|y)匹配x或者y


\
  轉義字符。能夠轉義左括號(,尖括號^,美圓符號 $, 感嘆號 !點 。 星號 *,管道符號|等,

\.
 轉義爲點字符(點字符在正則表達式中能夠匹配任意字符)

/*
  零個或多個字符

.*
  零個或多個任意字符(即匹配任意字符,包括空字符)

^$
  匹配「空字符」,「空行」

^.*$
    匹配任意字符串(僅限一行)

[^/.]
    匹配既非「正斜槓」也不是「點」的任意字符

[^/.]+
    匹配第一個字符既非「正斜槓」也不是「點」,後繼字符能夠是「正斜槓」或者「點」字符串

http ://
    匹配 http ://

^domain.*
    匹配以"domain"開始的字符串

^domain\.com$
    僅匹配 "domain.com"

-d
    測試字符串是否已存在的目錄  

-f
    測試字符串是不是已經存在的文件

-s
    測試字符串所指文件是否有「非零」值

如下爲相關例子:
1。將.htm 頁面映射到 .php

Options +FollowSymlinks
RewriteEngine On
RewriteRule ^(.*)\.htm$ $1.php [NC]

2。臨時重定向(R=302)與永久重定向(R=301)

RewriteEngine On
RewriteBase /
RewriteRule ^(.*)\.htm$ $.php [R,NC,L]
•該RewriteRule可以將.htm靜態頁面重定向到.php動態頁面
•若是經過.htm進入,瀏覽器地址欄會自動轉爲.php,這也是重定向的本質
•必須保證服務器上有對應的.php,不然會404
•瀏覽器和搜索引擎能夠同時經過.htm和.php訪問網頁
•若是該目錄上存在.htm,將被忽略
•RewriteBase定義了重寫基準目錄。
•例如,若是你將虛擬站點設置在/var/www目錄下,刪除這行將會致使重定向到h ttp://yourdomain.com/var/www/1.php 。顯然這是找不到的,並且你也不會但願用戶看見你的服務器的目錄結構。
•再舉個例子,若是RewriteBase /base/,那麼將會重定向到h ttp://yourdomain.com/base/1.php 。
•對於重寫基準目錄,咱們還能夠經過將$1.php變成/$1.php實現直接變換,這時就能夠將RewriteBase省略。
•字母R表示臨時重定向,至關於[R=302,NC]。關於重定向代碼,請參考h ttp://lesca.me/archives/htaccess-appendix.html 《HTTP協議重定向編碼》
•字母L表示若是能匹配本條規則,那麼本條規則是最後一條(Last),忽略以後的規則。

linux

永久得定向 R=301正則表達式

RewriteEngine On
RewriteRule ^(.*)$ h ttp://newdomain.com/$ [R=301,NC,L]
•這個規則告訴瀏覽器和搜索引擎,網站地址發生了永久性變動,用戶的URL請求將會被髮送給新的域名(主機)處理。
•因爲是重定向到新的主機地址,RewriteBase也就沒有出現的必要了。

3.爲何要用重定向?——重定向和URL重寫的區別
•經過重定向,瀏覽器知道頁面位置發生變化,從而改變地址欄顯示的地址
•經過重定向,搜索引擎意識到頁面被移動了,從而更新搜索引擎索引,將原來失效的連接從搜索結果中移除
•臨時重定向(R=302)和永久重定向(R=301)都是親搜索引擎的,是SEO的重要技術
•URL重寫用於將頁面映射到本站另外一頁面,若重寫到另外一網絡主機(域名),則按重定向處理

長短地址轉換
利用URL重寫,咱們能夠很方便地實現長短地址的轉換,可是用重定向就不合適了。

RewriteEngine On
RewriteRule ^grab /public/file/download/download.php

若訪問
h ttp://mysite/grab?file=my.zip

則會執行該頁面:
h ttp://mysite/public/files/download/download.php?file=my.zip

去掉www

options +FollowSymlinks
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*)$ h ttp://$1/$1 [R=301,NC,L]

加上www

optionEngine On
RewriteCond %{HTTP_HOST} ^(.*)$
RewriteRule (.*) h ttp://www\.%1/$1 [R=301,L]

支持多域名訪問
若是你不湊巧買到了不支持多域名的主機,那麼.htaccess或許能夠幫助你。如今假設你有域名domain-one.com和domain-two.com,而且在服務器根目錄有對應文件夾one和two,那麼經過下面的改寫就能讓Apache同時接受者兩個域名的請求:

RewriteCond %{HTTP_HOST} domain-one.com
RewriteCond %{REQUEST_URI} !^/one
RewriteRule ^(.*)$ /one/$1 [L]

RewriteCond %{HTTP_HOST} domain-two.com
RewriteCond %{REQUEST_URL} !^/two
RewriteRule ^(.*)$ /two/$1 [L]

改寫查詢字符串QUERY_STRING
查詢字符串是指URL請求中「問號」後面的部分。好比,h ttp://mysite/grab?foo=bar ?部分就是查詢字符串,其中變量名是foo,值是bar。
1.利用QSA轉換查詢字符串QUERY_STRING
QSA標誌( Query String Appending)用於在URI中截取查詢字符串,這個截取操做是經過小括號正則表達式實現的:

RewriteEngine On
RewriteRule /pages/(.+) /page.php?page=$1 [QSA]

•將會把請求/pages/123?one=two 映射到 /page.php?page=123&one=two
•注意幾乎是相同的,除了「問號」變成了「與」符號
•若是沒有QSA標誌,那麼會映射到/page.php?page=123。
•若是沒有用到小括號正則表達式,就不須要QSA
•小括號正則表達式能夠截取查詢字符串中的內容,可是若是沒有開啓QSA標誌,那麼在/page.php?page=$1中「問號」以後將會被剝離丟棄。這種特性能夠用於實現「剝離查詢字符串」

經過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]

利用RewriteCond改寫查詢字符串QUERY_STRING
RewriteEngine On
RewriteCond %{QUERY_STRING} foo=(.*)
RewriteRule ^grab(.*) /page.php?bar=%1

該規則將訪問請求htt p://mysite/grab?foo=bar轉換爲htt p://mysite/page.php?bar=bar
RewriteCond用於捕獲查詢字符串(QUERY_STRING)中變量foo的值,並存儲在%1中
QUERY_STRING是Apache定義的「變量=值」向量(數組)

QSA與RewriteCond一塊兒用

RewriteEngine On
RewriteCond %{QUERY_STRING} foo=(.+)
RewriteRule ^grab/(.*) /%1/index.php?file=$1 [QSA]

•會把/grab/foobar.zip?level=5&foo=bar 映射到 /bar/index.php?file=foobar.zip&level=5&foo=bar
•轉換後根目錄是bar目錄
•foobar.zip?level=5中的「問號」變成了foobar.zip&level=5中的「與」符號

剝離查詢字符串

只需在要開始剝離的連接後面加個「問號」,而且不要啓用QSA標誌,就可剝離查詢字符串

RewriteEngine On
RewriteCond %{QUERY_STRING} .
RewriteRule foo.php(.*) /foo.php? [L]

用.htaccess阻止User-agent
什麼是User-agent?User-agent用於瀏覽器向服務器「自報家門」,更確切的說是全部HTTP客戶端都得用User-agent向服務器「自報家門」,以便服務器對不一樣的客戶端做出不一樣響應。好比,某站點可能須要對瀏覽器、搜索引擎crawl還有各種下載工具做出不一樣的響應。服務器就是經過所謂的User-agent進行區分的。
若是你的服務器提供某些資源的下載,那麼你就必須多加當心諸如「迅雷」等下載軟件,由於它們可能把你網站資源吸乾,而且影響你的正常訪客訪問。爲此,咱們能夠利用Rewrite限制某些UA的訪問:


RewriteEngine On
RewriteCond %{HTTP_USER_AGENT} 2.0.50727 [NC,OR]
RewriteCond %{HTTP_USER_AGENT} ^BlackWido [NC,OR]
# ect...
RewriteRule . abuse.txt


•該規則限制「迅雷」客戶端下載資源,並將下載文件重置到abuse.txt
•HTTP_USER_AGENT是Apache的內置變量
•2.0.50727是迅雷User-agent的特徵字符串
•RewriteRule後面的「點」表示「任意URI」,也就是無論請求的是什麼,都輸出abuse.txt

文件訪問控制

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !^(.+)\.css$
RewriteCond %{REQUEST_FILENAME} !^(.+)\.js$
RewriteCond %{REQUEST_FILENAME} !special.zip$
RewriteRule ^(.+)$ /chat/ [NC]

•該規則將僅容許用戶請求.css, .js類型的文件,還有special.zip文件
•RewriteRule 後面指定了限制規則:映射到/char/目錄下處理
•RewriteCond 後面的「感嘆號」(!)起到了「否認」做用,它代表,對不知足後面正則表達式者應用RewriteRule規則,也就是對當前類型的文件將不該用規則
•RewriteCond 之間是以邏輯「與」鏈接的,也就是隻有當三個條件都不知足時才執行RewriteRule
•該規則也會限制訪問.htm, .jpg等格式
•該規則不能夠放在虛擬站點根目錄(/)下,不然會死循環
•若是是二級目錄,如/test/,那麼傳入RewriteCond的參數是以/test/開始的,所以從(.+)得到的文件名也含有/test/,讀者必須對此多加當心
•要想僅得到文件名,能夠將(.+)替換成([^/]+),而且去掉符號^,以下所示:

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !([^/]+)\.css$
RewriteCond %{REQUEST_FILENAME} !([^/]+)\.js$
RewriteRule ^(.+)$ /chat/ [NC]




RewriteEngine Off
#RewiteBase /
RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ [NC]
RewriteCond %{REQUEST_URI} !^/blog/
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ blog/$1

# 沒有輸入文件名的默認到到首頁
RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ [NC]
RewriteRule ^(/)?$ blog/index.php [L]

防盜鏈:
RewriteEngine on
#RewiteBase /
RewriteCond %{HTTP_REFERER} !^$ [NC]
RewriteCond %{HTTP_REFERER} !xxx.info [NC]
RewriteCond %{HTTP_REFERER} !(www\.)?baidu.com$ [NC]
RewriteCond %{HTTP_REFERER} !(www\.).google.com$ [NC]
RewriteRule \.(jpg|gif|png|bmp|swf|jpeg)$ /error/daolian.gif [R,NC,L]

【RewriteCond語法】
RewriteCond TestString CondPattern [flags]

rewritecond的其餘用法:
"-d"(目錄)
將TestString視爲一個路徑名並測試它是否爲一個存在的目錄。
"-f"(常規文件)
將TestString視爲一個路徑名並測試它是否爲一個存在的常規文件。
"-s"(非空的常規文件)
將TestString視爲一個路徑名並測試它是否爲一個存在的、尺寸大於0的常規文件。
"-l"(符號鏈接)
將TestString視爲一個路徑名並測試它是否爲一個存在的符號鏈接。
"-x"(可執行)
將TestString視爲一個路徑名並測試它是否爲一個存在的、具備可執行權限的文件。該權限由操做系統檢測。
"-F"(對子請求存在的文件)
檢查TestString是否爲一個有效的文件,並且能夠在服務器當前的訪問控制配置下被訪問。它使用一個內部子請求來作檢查,因爲會下降服務器的性能,因此請謹慎使用!
"-U"(對子請求存在的URL)
檢查TestString是否爲一個有效的URL,並且能夠在服務器當前的訪問控制配置下被訪問。它使用一個內部子請求來作檢查,因爲會下降服務器的性能,因此請謹慎使用!

【RewriteRule語法:】
RewriteRule Pattern Substitution [flags]

【flags】
"chain|C"(連接下一規則)


"cookie|CO=NAME:VAL:domain[:lifetime[:path]]"(設置cookie)


"env|E=VAR:VAL"(設置環境變量)


"forbidden|F"(強制禁止URL)


"gone|G"(強制廢棄URL)


"handler|H=Content-handler"(強制指定內容處理器)


"last|L"(結尾規則)


"next|N"(從頭再來)


"nocase|NC"(忽略大小寫)


"noescape|NE"(在輸出中不對URI進行轉義)


"nosubreq|NS"(不對內部子請求進行處理)


"proxy|P"(強制爲代理)


"passthrough|PT"(移交給下一個處理器)


"qsappend|QSA"(追加查詢字符串)


"redirect|R [=code]"(強制重定向)


"skip|S=num"(跳事後繼規則)


"type|T=MIME-type"(強制MIME類型)

RewriteRule ^(.+\.php)s$ $1 [T=application/x-httpd-php-source]apache

示例:數組

RewriteEngine On
RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ RewriteCond %{REQUEST_URI} !^/blog/ RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule ^(.*)$ /blog/$1 # 沒有輸入文件名的默認到到首頁 RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ RewriteRule ^(/)?$ blog/index.php [L]

RewriteEngine On】
表示重寫引擎開,關閉off,做用就是方便的開啓或關閉如下的語句,這樣就不須要一條一條的註釋語句了。
瀏覽器

RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$】
這是重寫條件,前面%{HTTP_HOST}表示當前訪問的網址,只是指前綴部分,格式是www.xxx.com不包括「http://」和「/」,^表示 字符串開始,$表示字符串結尾,\.表示轉義的. ,若是不轉義也行,推薦轉義,防止有些服務器不支持,?表示前面括號www\.出現0次或1次,這句規則的意思就是若是訪問的網址是xxx.com或者 www.xxx.com就執行如下的語句,不符合就跳過。
服務器

【RewriteCond %{REQUEST_URI} !^/blog/】
也是重寫條件,%{REQUEST_URI}表示訪問的相對地址,就是相對根目錄的地址,就是域名/後面的成分,格式上包括最前面的「/」,!表示非,這句語句表示訪問的地址不以/blog/開頭,只是開頭^,沒有結尾$cookie

【RewriteCond %{REQUEST_FILENAME} !-f】
【RewriteCond %{REQUEST_FILENAME} !-d】
這兩句語句的意思是請求的文件或路徑是不存在的,若是文件或路徑存在將返回已經存在的文件或路徑

RewriteRule ^(.*)$ /blog/$1】
重寫規則,最重要的部分,意思是當上面的RewriteCond條件都知足的時候,將會執行此重寫規則,^(.*)$是一個正則表達的 匹配,匹配的是當前請求的URL,^(.*)$意思是匹配當前URL任意字符,.表示任意單個字符,*表示匹配0次或N次(N>0),後面 /blog/$1是重寫成分,意思是將前面匹配的字符重寫成/blog/$1,這個$1表示反向匹配,引用的是前面第一個圓括號的成分,即^(.*)$中 的.* ,其實這兒將會出現一個問題,後面討論。

 

【RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$】
【RewriteRule ^(/)?$ blog/index.php [L]】
這兩句的意思是指請求的host地址是www.xxx.com是,若是地址的結尾只有0個或者1個「/」時,將會重寫到子目錄下的主頁,我猜測這主要由於重寫後的地址是不能自動尋找主頁的,須要本身指定。

 

如今說說出現的問題,RewriteRule ^(.*)$ /blog/$1 前部分 ^(.*)$ 將會匹配當前請求的url。
例如:請求網址是http://www.xxx.com/a.html,究竟是匹配整個http://www.xxx.com/a.html,仍是隻匹配/a.html即反斜槓後面的成分,仍是隻匹配a.html。
答 案是:(根據RewriteBase規則規定,若是rewritebase 爲/,將會匹配a.html,不帶前面的反斜槓,因此上條語句應該寫成RewriteRule ^(.*)$ blog/$1(不帶/),不過實際應用上帶上前面的反斜槓,也能夠用,可能帶不帶都行。如今問題出來了,若是不設置rewritebase 爲/ ,將會匹配整個網址http://www.xxx.com/a.html,顯然這是錯誤的,因此應該添加這條:RewiteBase /)有誤,本身測試通不過,因此確的應該是 RewriteRule 中的跳轉部分加上 http://協議

 

還有一個問題是,不能保證每一個人輸入的網址都是小寫的,若是輸入大寫的呢,linux系統是區分大小寫的,因此應該在RewriteCond後添加[NC]忽略大小寫的。

至此,完整的語句應該是:

 

RewriteEngine On
RewiteBase / RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ [NC] RewriteCond %{REQUEST_URI} !^/blog/ RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule ^(.*)$ blog/$1 # 沒有輸入文件名的默認到到首頁 RewriteCond %{HTTP_HOST} ^(www\.)?xxx\.com$ [NC] RewriteRule ^(/)?$ blog/index.php [L]

 

以上來自www.cnblogs.com/adforce/archive/2012/11/23/2784664.html help.vit.cn/item/category/htaccess 和 lesca.me/

相關文章
相關標籤/搜索