來源:互聯網
上載者:User
關鍵字
htmlspecialchars和htmlentities處理特殊字元的一些思考
在firefox中,使用“查看”菜單中的“頁面原始碼”查看html原始碼 跟 選中要看的內容然後點擊”查看選中部分的原始碼“ ,得到的原始碼不相同,我們寧可相信前者,而不要相信後者。舉例來說:頁面為gbk的,中有一個表單,通過表單中的輸入框輸入這個字元“・”,儲存到資料 庫中的是“・”,如果接著將它查出來在頁面上顯示(gbk字元),他會顯示回原樣:“・”,如果使用“查看選中部分的原始碼”查 看,他的html原始碼仍然是這個怪異的點號,但是如果使用“頁面原始碼”查看,他會現出原形“・”。同樣很多字元也一樣:❤
因為這個符號在資料庫中以“・”儲存(為什麼要以這個儲存,主要是因為你的頁面是gbk的,無法正常傳輸這個字元,因此只能轉換成特殊字元才能傳到伺服器),所以每次讀出的時候如果不經過轉換直接顯示,也會顯示為原來的那個點,但是我們一般在伺服器端向用戶端發送字串時都要對其中的特殊字元進行處理,比如使用htmlentities函數。這樣的話,就會將字元中的&轉換為&,點號也就無法正常顯示了。
在這個過程中,我考慮,我們應該按照什麼流程來處理表單傳入的字串:(這裡預設magic_quotes_gpc設定為0,以後任何項目中也推薦這樣設定,如果gpc為1,那麼首先對所有資料進行stripslashes處理):
htmlspecialchars mysql_real_escape 直接
form ------------------------------> -------------------------------> DB ---------> html
還是:
mysql_real_escape htmlspecialchars
form -------------------------------> DB ---------------------------------> html
其實我這裡認為兩者基本都一樣,最後返回的html結果都正確,都能處理好資料。我之前使用的是第二種形式,其中遇到了一些問題,主要是在表單出錯後返回,讓客戶修改資料重新提交時遇到的問題,原來是直接將表單提交的資料返回(不經過任何處理)重新賦給表單,但對於某些特殊的字元,比如單引號或者雙引號,再返回時就 會出現異常的情況,或者不顯示,或者顯示不正常。於是需要我們對資料進行htmlspecialchars處理。於是我開始考慮第一個流程,如果表單驗證錯誤,可以在htmlspecialchars後面返回,將資料重新賦給表單而不會導致表單內容出錯的問題。但是第一個流程有個致命的問題,我們在資料庫中要儲存顯示的資料呢還是要儲存原始的資料呢?當然最好是原始的資料。因此我們還得使用第二個流程,在返回錯誤頁面的時候,我們也得使用 htmlspecialchars進行轉換,雖然比較麻煩,但這樣不會出現問題。
在研究htmlentities和htmlspecialchars兩個函數的不同點的過程中,我們測試這個字元傳:“gbk鐘沒有的”。經過 htmlspecialchars($str, ENT_QUOTES),這個字串沒有改變。但是經過htmlentities($str)甚至htmlentities($str, ENT_QUOTES, 'GB2312')(應該是gbk,但這裡不支援gbk),結果分別變為:“gbkç姏]ÓеĔ 和 “gbkç姏]有的”。於是決定不管在任何情況下都應該使用htmlspecialchars來代替htmlentities,同時也不需要自己寫什麼 _myhtmlentities來修複htmlentities原有的問題。當然htmlentities出現亂碼的原因不光是因為它本身的問題,也是因 為傳入的字元是在gbk中才有的,gb2312中沒有,但只能使用gb2312來處理,於是出現錯誤。
不過關於資料庫中記錄網頁內容字元的問題,到底存真實的,還是html轉義過的,我在一本很好的教材上看到並也認可:其實都可以,我個人現在用的是存轉義後的字元,然後,從資料庫取出時直接顯示在網頁,無論是文章標題還是內容。至於編碼,當然是全utf8。寧可犧牲執行效率,也不為這個傷神。