2012-06-27 37 views
3

我正在使用無處不在jquery validate plugin進行表單驗證。它支持使用metadata plugin來添加驗證規則以形成元素。主要煩惱與jQuery元數據插件和jQuery驗證插件

我正在使用此功能。當驗證查找這些規則它使這個元素的電話:

$(element).metadata()[meta] 

其中meta是存儲這些規則的前綴。例如

<input data-validate="{maxLength: 12}" name='foo'/> 

元的值將被設置爲'validate'來獲取這些屬性。但這裏有一個主要問題!

這裏是元數據插件不解析數據屬性爲JSON什麼:

var getObject = function(data) { 
    if(typeof data != "string") return data; 
    data = eval("(" + data + ")"); //oh no!!!!! 
    return data; 
} 

if (settings.type == "html5") { 
    var object = {}; 
    $(elem.attributes).each(function() { 
     var name = this.nodeName; 
     if(name.match(/^data-/)) name = name.replace(/^data-/, ''); 
     else return true; 
     object[name] = getObject(this.nodeValue); 
    }); 
} 

那麼最終發生的是,元數據解析所有data-*屬性,並試圖EVAL內容!只要你包含一個不包含json的數據屬性,就會破壞這些東西。

現在的問題:

這似乎是元數據和驗證都是「嘗試和真正的」插件。這是使用人們剛剛生活的元數據插件的已知副作用嗎?

我通常不喜歡修改插件代碼適合我的項目需要,但這個好像我應該:

  • 解決元數據插件不能盲目EVAL的東西,而不是使用eval或
  • 修復驗證插件使用.data()代替元數據插件

此外,有沒有一些其他的方式解決此其他然後修改元數據插件

帖子賞金編輯: 我應該說得更清楚一點,我會對如何發生這種情況的一些討論感興趣。在規範驗證插件和插件之間如何存在如此巨大的錯誤,這些插件在resig編寫的任何地方都可以使用。

一個修復很簡單,我已經應用它(我選擇修改驗證插件使用$ .data當'meta'被定義時) - 我給這裏150點的想法是爲什麼這仍然是一個問題(也許它不是!)

+0

當然,這是一種很奇怪的事情,因爲表單在HTML5中有驗證。我一直在支持它的瀏覽器中使用本地驗證,然後使用JS來填充舊版本的行爲。 –

回答

7

正如您發現的,「錯誤」(使用eval)在於元數據插件,而不是驗證插件。

鏈接到的元數據插件的版本實際上是一個叉; jQuery團隊擁有official repo。如果你看一下commit history,你會看到,沒有發生過任何真正的代碼更新自2007年以來2011年4月在插件officially deprecated

(約翰Resig的2008年7月在博客HTML5 data- attributes,和支持jQuery的核心抵達1.4.3,這是在October 2010發佈。)

所以我想回答你的「這是如何發生」的問題,就是你不要以爲使用插件了:-)

更新:"official" repo現在正在「由jQuery基金會孤立的項目」。)

至於驗證插件,除了demosmeta選項中的一些外,我在文檔中找不到任何關於元數據插件的提及。目前正在進行的工作是添加support for data- attributesdeprecate the metadata plugin,所以希望下一個版本準備就緒後,元數據插件最終可以放棄。

+0

我很感謝你的詳細答案,尤其是因爲jQuery頁面本身(在'學習'子域,不會少!)仍然[崇尚](http://learn.jquery.com/plugins/advanced-plugin-concepts /)使用元數據插件 - 儘管「官方回購」不再存在。 – EleventyOne

+0

@EleventyOne感謝您的評論;我在learn.jquery.com上提供了一個[ticket](https://github.com/jquery/learn.jquery.com/issues/409)與好的(並且毫無疑問是忙碌的)人員。 –

0
data = eval("(" + data + ")"); //oh no!!!! 

一個的方式與

data = $.parseJSON(data); // oh yes!!! 

居然來取代它,當你的「數據」。數據與()方法,它`試圖解析它,並做得很好。最好從使用它的元素中檢索數據。之後,您將獲得一個將被連接到節點的緩存對象,並會爲您提供更快的屬性值。

Here you are這是分支版本的元數據插件,它不會評估所有獲得的元數據插件。有一件事你必須知道。你應該像引用JSON一樣引用字典的所有部分,但並不總是用雙引號。

{'foo': 'bar', "m": true, "b": 1}; // works 
{foo: 'bar', m: true, b: 1}; // won`t work 
+2

爲避免必須爲元數據編寫有效的JSON,可以添加一行,如'data = data.replace(/([a-zA-Z _ $] [\ w $] *)\ s *:/ g,' 「$ 1」:');在解析之前進入getObject函數。這個想法是找到對象鍵並向它們添加引號。正則表達式可能需要一些工作,雖然 – jackwanders

+0

我認爲正則表達式,它會做到這一點,並只做引用替換,使其更容易一些。但是,謝謝。 – Flops

+0

我認爲有效的json是插件用戶的有效需求;一切都只是一個黑客 – mkoryak