2009-04-15 28 views
12

我有一個應用程序,用戶在其中輸入文本到表單中。我如何在保存之前清理用戶輸入以進行正確的內容編碼?

將數據保存到MySQL數據庫(排序規則:utf8_general_ci),然後以XML(編碼:UTF-8)形式輸出。

問題是人們傾向於從其他來源剪切和粘貼他們的信息,例如Microsoft Word文檔或PDF。

此輸入文本往往有其是不正確的輸出編碼的字符,如「智能引號」,它來自於一個文檔中Windows-1252 encoding

這會導致問題,顯然,轉化或在XML否則工作時的事情因爲這些角色是非法的。

那麼,如何消毒輸入?

此前,我已經使用了一些相當蠻力的方法,比如"de-moronize" script,它由一長串搜索和替換操作組成。

這仍然是最好的方法嗎?有沒有其他方法?

我可以只在表單上設置accept-charset attribute並讓瀏覽器爲我做?

如果是這樣,哪些瀏覽器會這樣做,並可能有任何問題?

另外,我的數據庫如何接受這些字符,它們是UTF-8中的保留/控制字符?

正如你所看到的,我有足夠的瞭解編碼知道我有一個問題,但我現在有點不在我的深度...

TIA

回答

9

此輸入文本往往有其是不正確的輸出編碼的字符,如「智能引號」,它來自於Windows的文檔事1252編碼

「智能引號」(cp1252中的字節147和148)是完全有效的Unicode字符,U + 201C和U + 201D。您的應用程序應該能夠無縫處理它們;如果沒有,你做錯了,很可能所有非ASCII字符都會失敗。

無論字符是從某人輸入還是從Word中粘貼出來,瀏覽器都應該向您的應用程序提交UTF-8編碼的字符,應該將相同的UTF-8字節存儲到數據庫中。

如果瀏覽器沒有以UTF-8格式提交,您可能無法設置包含表單的HTML頁面的字符集。這可以通過使用來完成:

Content-Type: text/html;charset=utf-8 

HTTP標頭和/或:

<meta http-equiv="Content-Type" content="text/html;charset=utf-8" /> 

元件在<頭>。

我可以在表單上設置accept-charset屬性並讓瀏覽器爲我做這件事嗎?

沒有,接收字符集基本是沒用由於IE瀏覽器,這曲解了它的意思是「嘗試使用此charset如果頁面上的一個不能編碼我們想要的人物」,而不是「始終使用該字符集」。這意味着如果您使用accept-charset,您最終可能會混合使用一次提交的編碼,無法找出哪個編碼是哪個編碼。太好了!

我的數據庫如何接受這些字符,這些字符是UTF-8中的保留/控制字符?

在MySQL中,UTF-8只是一個排序規則,用於比較和排序。它仍然將數據存儲爲字節,並且不關心它們是否不是有效的UTF-8序列。

無論如何,在您的應用中解碼和檢查傳入的UTF-8序列是個好主意,因爲在現代Unicode中無效的「短序列」可以隱藏仍會被舊版瀏覽器識別的「<」字符至少IE6 SP2之前,Opera 7)。

ETA:

所以,我進入包含字節146

沒有一個字符串,您輸入Unicode字符U + 201B。瀏覽器處理Unicode字符,而不是字節,直到它必須將序列化表單提交給服務器。然後它決定如何將字符轉換爲字節,如果頁面以UTF-8處理,它將始終選擇UTF-8。 (如果它不是UTF-8,瀏覽器往往以非標準兼容的方式作弊:對於所有不適合編碼的字符,它會將它們編碼爲HTML字符引用,如'&# 8217;'這是錯誤的,因爲你現在無法區分瀏覽器轉義的'&'和真實的用戶類型'&'之間的區別,並且它是錯誤的,因爲如果你隨後將引用作爲未轉義的HTML回顯看起來像你得到它的權利,這實際上你只是做了一個大的舊的安全漏洞。)

它進入數據庫爲146

真的,一個'\ x92'字節,不是'\ xC2 \ x92','\ xE2 \ x80 \ x99'或'&#146;'?

它出來時,我公司生產的(UTF-8編碼),XML,爲146從瀏覽器

沒有抱怨然後,它沒有出來作爲一個146字節。當在XML文件中給出一個純粹的'\ x92'時,瀏覽器將會投訴。(不是一個HTML文件,其中出現無效的UTF-8序列作爲缺少字符的字形)。

我懷疑它是作爲'&#146'出現的'字符引用,它是格式良好的儘管字符U + 0092是C1控制集的一部分,所以不會渲染任何有用的東西)。如果發生這種情況,您的表單頁面將不會被視爲UTF-8,而且您正在遭受上述瀏覽器自動轉義提交問題。

+0

OK「字節147和148是完全有效的Unicode字符,U + 201C和U + 201D」是我沒有得到的部分。瀏覽器無法識別粘貼測試的編碼。它如何知道他們是CP1252智能報價?當然,他們只是字節!或者是147-148的使用如此特殊,可以假設這是安全的? – AmbroseChapel 2009-04-15 20:20:33

2

你可以嘗試的Perl Encode模塊。它支持許多字符集之間的轉換,包括couse的UTF-8。我剛剛檢查了我的Perl安裝,並且還支持「cp1252」,根據維基百科,它只是Windows-1252的另一個名稱。您可以檢查自己用下面的襯板安裝:

perl -MEncode -e 'print map {"$_\n"} Encode->encodings(":all");' 
+0

乾杯。我已經做到了,我準備好了。 – AmbroseChapel 2009-04-15 08:34:46

1

「我可以在表單上設置accept-charset屬性並讓瀏覽器爲我做這件事嗎?」

只有當你準備信任「瀏覽器」時 - 這可能適用於某些應用程序,但總的來說,它會讓你自己面對惡作劇(或更糟)。

(另見bobince的有關IE的警告......)

伊恩

相關問題