2011-07-14 85 views
1

我已經存儲在htaccess重寫循環?

/public/upload/* 

例如用戶上傳的文件:

/public/upload/gallery/segway/child-on-a-segway.jpg 

我目前的.htaccess規則已經消除/public部分,但我仍然需要擺脫/upload部分,但是,僅適用於具有給定擴展名但不包含在其他目錄中的文件,例如jsimg。我目前的.htaccess看起來像這樣(典型的Zend框架項目):

RewriteEngine On 

RewriteRule ^\.htaccess$ - [F] 

RewriteCond %{REQUEST_URI} ="" 
RewriteRule ^.*$ /public/index.php [NC,L] 

RewriteCond %{REQUEST_URI} !^/public/.*$ 
RewriteRule ^(.*)$ /public/$1 

RewriteCond %{REQUEST_FILENAME} -f 
RewriteRule ^.*$ - [NC,L] 

RewriteRule ^public/.*$ /public/index.php [NC,L] 

在擺脫/upload部分工作的希望,我寫這在我的.htaccess的末尾:

RewriteCond %{REQUEST_URI} ^(?<!upload|img|js|less|css)/.*(jpg|mp3|png)$ 
RewriteRule ^(.*)$ /upload/$1 

基本上,如果一個文件具有jpg,png或mp3擴展名,並且它的路徑不以「upload」,「js」,「css」,「img」或「less」開頭,則將前綴「上傳」到請求URI 。那麼,它失敗了。當我在地址欄中輸入:http://example.com/gallery/1/php193A.jpg,我得到一個303錯誤:

You don't have permission to access /upload//public/upload/public/upload/public/upload/public/upload/public/upload/public/upload/public/upload/public/upload/public/gallery/1/php193A.jpg/1/php193A.jpg/gallery/1/php193A.jpg/1/php193A.jpg/upload/public/gallery/1/php193A.jpg/1/php193A.jpg/gallery/1/php193A.jpg/1/php193A.jpg/upload/public/upload/public/gallery/1/php193A.jpg/1/php193A.jpg/gallery/1/php193A.jpg/1/php193A.jpg/upload/public/gallery/1/php193A.jpg/1/php193A.jpg/gallery/1/php193A.jpg/1/php193A.jpg...

和URL的推移和對幾十行,就好像是循環。

這是我第一次處理.htaccess重寫規則。我會很感激一些幫助他們設置直線,因爲我完全迷失在這裏。提前致謝。

+0

我實際上是在錯誤信息笑了相當困難,ahaha – Cyclone

+0

我的客戶不會覺得太好玩了,雖然:( – mingos

+0

這就是爲什麼我目前正在調試它爲你笑 – Cyclone

回答

1

你說你「在我的.htaccess」「的末尾寫了這個。 TBH我看不出如何應該達到這個規則(規則順序事項)而不會改變一些其他規則(比如,刪除L標誌)。

讓我們來看看這個請求:/gallery/segway/child-on-a-segway.jpg

  1. 將通過這條規則被改寫爲/public/gallery/segway/child-on-a-segway.jpgRewriteRule ^(.*)$ /public/$1

  2. 因爲沒有這樣的文件,這將進一步此規則改寫爲/public/index.phpRewriteRule ^public/.*$ /public/index.php [NC,L]。由於[L]標誌重寫進入下一次迭代。

  3. 在第二次重寫迭代時,該規則RewriteRule ^.*$ - [NC,L]發現/public/index.php確實存在並終止了任何進一步的重寫。


考慮上述所有它變得很明顯,這樣的附加規則需要在中間的某個地方放置,而無需修改任何現有規則。這是規則我出來與你的要求相匹配(根據你試圖改寫):

RewriteCond %{REQUEST_URI} !^/(public|img|js|css)/.*$ 
RewriteCond %{DOCUMENT_ROOT}/public/upload%{REQUEST_URI} -f 
RewriteRule ^(.+\.(jpg|png|mp3))$ /public/upload%{REQUEST_URI} [NC,L] 

正確的地方來放置它,在我看來,將這個規則之前:RewriteRule ^(.*)$ /public/$1。這樣。htaccess將具有以下內容:

RewriteEngine On 

RewriteRule ^\.htaccess$ - [F] 

RewriteCond %{REQUEST_URI} ="" 
RewriteRule ^.*$ /public/index.php [NC,L] 

RewriteCond %{REQUEST_URI} !^/(public|img|js|css)/.*$ 
RewriteCond %{DOCUMENT_ROOT}/public/upload%{REQUEST_URI} -f 
RewriteRule ^(.+\.(jpg|png|mp3))$ /public/upload%{REQUEST_URI} [NC,L] 

RewriteCond %{REQUEST_URI} !^/public/.*$ 
RewriteRule ^(.*)$ /public/$1 

RewriteCond %{REQUEST_FILENAME} -f 
RewriteRule ^.*$ - [NC,L] 

RewriteRule ^public/.*$ /public/index.php [NC,L] 

我已測試它 - 它的工作原理。它可能不是最優化的文件查找執行(-f),但考慮到它只適用於數量有限的擴展(這是一個很好的要求),它應該沒問題(如果它是爲每個擴展然後它會在繁忙的服務器/負載下減速系統)。

P.S. 據我所知,(?<模式意味着「可變長度後視」(儘管我不是100%確定)。

+0

哇,非常感謝你!它的作用像一個魅力,我懷疑我自己曾經想出這個。 )如果客戶端請求擴展的數量可能會變大,例如.flv文件也會上傳,但它仍然是一個有限的集合。再次感謝。 – mingos