$.ajax在谷歌瀏覽器傳入中文亂碼的情況
有運營同學反映,後臺編輯的一箇中文顯示名稱,前臺亂碼了,於是乎~~
先看程式碼是否get請求沒轉碼:
[javascript] view plain copy- $.ajax({
- type: 'POST',
- url: '/admin/updatedisplayname}',
- data: {displayName:displayName},
- success: function(res){
- alert(1);
- },
- error: function() {
-
alert(2);
- },
- dataType: 'json'
- })
這段程式碼不管怎麼看,也沒有問題,post請求過去的,應該不會存在亂碼問題,自己測了下,修改回去了,沒亂碼(火狐)
奇怪~
問了下,對方用的是谷歌,檢查他的瀏覽器編碼有沒特殊設定過,沒有,一切正常。
納悶,回來在谷歌測試下,暈死,果然重現,亂碼了,哈哈,那就好辦,查~
看看請求頭資訊啥的,發現使用$.ajax請求的時候有一個值有問題
chrome:contentType: 'application/x-www-form-urlencoded'
ff:contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
難道是這個在作祟,如果乎~
[javascript] view plain copy- $.ajax({
- type: 'POST',
- url: '/admin/updatedisplayname}',
- data: {displayName:displayName},
- contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
- success: function(res){
- alert(1);
- },
-
error: function
- alert(2);
- },
- dataType: 'json'
- })
莫不是有啥玄機,檢視jQuery手冊
contentTypeString
(預設: "application/x-www-form-urlencoded") 傳送資訊至伺服器時內容編碼型別。預設值適合大多數情況。如果你明確地傳遞了一個content-type給 $.ajax() 那麼他必定會發送給伺服器(即使沒有資料要傳送)
為毛我在不傳入這個值的時候,火狐會加上 charset=UTF-8呢?
看看jquery原始碼:
[javascript] view plain copy- ajaxSettings: {
- url: location.href,
- global: true,
- type: "GET",
- contentType: "application/x-www-form-urlencoded",
- processData: true,
- async: true,
- /*
- timeout: 0,
- data: null,
- username: null,
- password: null,
- traditional: false,
- */
- // Create the request object; Microsoft failed to properly
- // implement the XMLHttpRequest in IE7 (can't request local files),
- // so we use the ActiveXObject when it is available
- // This function can be overriden by calling jQuery.ajaxSetup
- xhr: window.XMLHttpRequest && (window.location.protocol !== "file:" || !window.ActiveXObject) ?
- function() {
- returnnew window.XMLHttpRequest();
- } :
- function() {
- try {
- returnnew window.ActiveXObject("Microsoft.XMLHTTP");
- } catch(e) {}
- },
- accepts: {
- xml: "application/xml, text/xml",
- html: "text/html",
- script: "text/javascript, application/javascript",
- json: "application/json, text/javascript",
- text: "text/plain",
- _default: "*/*"
- }
- },
- contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
果然發現了幾個隱藏的bug,不過像這樣的直接使用$.ajax一般只有後臺系統才用用到,而我們的後臺系統是可以不相容google的,所以當時測試的時候可能沒測到。
不過,又有問題,有同學沒有加,但是測試是ok的,谷歌不亂碼,各種不淡定啊。。。。
再查~
首先想到檢查jquery版本,果然,這哥們是用jquery1.7.2,而我用的是1.4.2,檢視1.7.2的原始碼:
[javascript] view plain copy- ajaxSettings: {
- url: ajaxLocation,
- isLocal: rlocalProtocol.test( ajaxLocParts[ 1 ] ),
- global: true,
- type: "GET",
- contentType: "application/x-www-form-urlencoded; charset=UTF-8",
- processData: true,
- async: true,
- /*
- timeout: 0,
- data: null,
- dataType: null,
- username: null,
- password: null,
- cache: null,
- traditional: false,
- headers: {},
- */
- accepts: {
- xml: "application/xml, text/xml",
- html: "text/html",
- text: "text/plain",
- json: "application/json, text/javascript",
- "*": allTypes
- },
- contents: {
- xml: /xml/,
- html: /html/,
- json: /json/
- },
- responseFields: {
- xml: "responseXML",
- text: "responseText"
- },
- // List of data converters
- // 1) key format is "source_type destination_type" (a single space in-between)
- // 2) the catchall symbol "*" can be used for source_type
- converters: {
- // Convert anything to text
- "* text": window.String,
- // Text to html (true = no transformation)
- "text html": true,
- // Evaluate text as a json expression
- "text json": jQuery.parseJSON,
- // Parse text as xml
- "text xml": jQuery.parseXML
- },
- // For options that shouldn't be deep extended:
- // you can add your own custom options here if
- // and when you create one that shouldn't be
- // deep extended (see ajaxExtend)
- flatOptions: {
- context: true,
- url: true
- }
- },
暈死,在1.7.2中居然加上了charset=UTF-8,
各種~~~~,再探~1.7原始碼裡面也是沒有的
好吧,1.7.2裡面沒有這個問題。
結論:
1、使用1.7.2之前的版本,在使用$.ajax的時候需要自行設定contentType否則,谷歌會亂碼。
2、跟瀏覽器也有關係,火狐就可以自動加上utf-8而谷歌則不會,也行jquery團隊發現這個問題,所以就在最新版更正了這個問題。
測試及生成環境:
1、Java環境,打包gbk,頁面編碼gbk,tomcat中URIEncoding配置utf-8等,也許應該跟這些伺服器配置也是有關係的,就不深究下去了。
猜測:一般post表單請求的請求資料編碼是按照頁面裡面的meta指定的編碼格式編碼的,我們頁面是gbk的,所以在谷歌瀏覽器在未指定ajax的contentType引數的時候採用預設頁面編碼方式gbk編碼然後傳送到伺服器端,而我們tomcat裡面的URIEncoding是utf-8的,所以就兩邊編碼不一樣,就亂碼了,顯式的指定一下就ok。不過貌似ajax統一都是utf-8的來編碼的,就算不指定也不會有問題,莫不是谷歌。。。。