2010-08-23 50 views
0

我已經在這裏打了一堵牆。據我所知,這應該起作用,但事實並非如此。Apache重寫規則和跳過邏輯

我有一個本地開發地址,包含* .localhost的通配符子域,以及/ [0-9]/somestring的友好URL。我想要做的是有username.localhost/1/pagelocalhost?pageId=1&username=username。複雜性在於試圖將username.localhost的主頁以及各個頁面(即username.localhost/1/page)都起作用。

RewriteRule ^([0-9]+)/[a-zA-Z0-9\-\_\,\.]+$ - [S=1] 
RewriteCond %{HTTP_HOST} !^www.* [NC] 
RewriteCond %{HTTP_HOST} ^([^\.]+)\.localhost 
RewriteRule ^index.php$ index.php?username=%1 
RewriteRule ^([0-9]+)/[a-zA-Z0-9\-\_\,\.]+$ index.php?pageId=$1&username=%1 

使用/ 1 /頁面頁面,第一條規則用於跳過匹配和跳過,但無法正確重寫。但是,如果我刪除前兩條規則,它會重寫/ 1 /頁面就好了。

就好像它沒有跳過,但如果我將它更改爲S = 2,它將跳過這兩個規則。哎呀。有任何想法嗎?

回答

1

從我所知道的,它實際上做你期望它做。只有在這樣做之後,它會在你的規則集中進行第二次嘗試,這會弄亂一切。發生了什麼事更具體是這樣的:

  • 請求http://username.localhost/1/page
  • 輸入1/page匹配的規則,S=1應用
  • 輸入1/page符合第三條規則,URL改寫爲index.php?pageId=1&username=username
  • 通過mod_rewrite執行內部重定向(目前爲止都很好,但是...)
  • mod_rewrite處理內部重定向,並且sta RTS處理規則再次
  • 輸入index.php不匹配的第一個規則,S=1不施加
  • 輸入index.php匹配第二規則,URL被改寫爲index.php?username=username
  • (內部重定向再次發生時,相同的重寫被執行,但mod_rewrite檢測重定向循環,現在停止處理)

有幾種不同的方式來解決這個問題,但我認爲最簡單的一個在這裏只是確保文件不存在,然後從最後一個RU滾動模式樂成前一個條件:

# Make sure we haven't rewritten to a file yet (the "directory" gets processed 
# before DirectoryIndex index.php is applied) 
RewriteCond %{REQUEST_FILENAME} !-f 
# Check that the input doesn't match the pattern we want handled later 
RewriteCond $0   !^([0-9]+)/[a-zA-Z0-9_,.-]+$ 
RewriteCond %{HTTP_HOST} !^www.* [NC] 
RewriteCond %{HTTP_HOST} ^([^\.]+)\.localhost 
RewriteRule ^.*$ index.php?username=%1 

RewriteRule ^([0-9]+)/[a-zA-Z0-9_,.-]+$ index.php?pageId=$1&username=%1 

編輯:以上版本還捕捉的東西不符合你的頁面模式,就像他們index.php?username=username,這可能是不希望的。以下將避免這一點,並且無論如何更簡潔一些:

RewriteCond %{HTTP_HOST} !^www.* [NC] 
RewriteCond %{HTTP_HOST} ^([^\.]+)\.localhost 
RewriteRule ^$ index.php?username=%1 

RewriteRule ^([0-9]+)/[a-zA-Z0-9_,.-]+$ index.php?pageId=$1&username=%1 
+0

感謝您的回答。我可以看到一秒鐘如何貫穿整個規則的邏輯可能會在整個事情中引發一場大問題。對不起,如果我有點密集,但我無法跟隨你的解決方案如何解決它。 REQUEST_FILENAME出來是index.php,它總是會存在的,因此嘗試這似乎並沒有氾濫。 – 2010-08-24 13:18:57

+0

@Zurahn - 對於'http:// username.localhost /'的請求將有'/ website/root/dir /'的初始'%{REQUEST_FILENAME}',因爲域後沒有請求路徑。這不是一個文件,所以在第一遍中''-f'的條件是真的。在隨後的傳遞過程中(在這種情況下,因爲有'RewriteRule',但是如果應用了DirectoryIndex,情況也是如此),'%{REQUEST_FILENAME}'變成'/ website/root/dir/index.php',是一個文件,導致條件失敗,並且不允許意外再次執行第一次重寫。 – 2010-08-24 14:32:27

+0

感謝您的幫助。我會與你提供的東西一起工作,並認爲我應該能夠管理它。 – 2010-08-24 14:49:29