簡體   English   中英

通過Python的eval()運行JSON?

[英]Running JSON through Python's eval()?

除了最好的做法,有沒有令人信服的理由這樣做?

我正在編寫一個post-commit鈎子,用於Google Code項目,該項目通過JSON對象提供提交數據。 GC提供HMAC身份驗證令牌以及請求(在JSON數據之外),因此通過驗證該令牌,我可以高度確信JSON數據是良性的(因為不信任Google)並且有效。

我自己(簡短)的調查表明,JSON恰好是完全有效的Python,除了"\\/"轉義序列 - GC似乎沒有生成。

因此,當我使用Python 2.4(即沒有json模塊)時, eval()看起來真的很誘人。

編輯:為了記錄,我不是在問這是不是一個好主意。 非常清楚它不是,我非常懷疑即使我最終將它用於這個項目,我也會將這項技術用於任何未來的項目。 我只是想確保我知道如果我這樣做會遇到什么樣的麻煩。 :-)

如果你對你的腳本工作正常一段時間感覺很舒服,然后在一些不起眼的邊緣情況下隨機失敗,我會選擇eval。

如果你的代碼很健壯很重要,我會花時間添加simplejson。 你不需要C部分來加速,所以將一些.py文件轉儲到某個目錄中真的不難。

作為可能咬你的東西的一個例子,JSON使用Unicode而simplejson返回Unicode,而eval返回str:

>>> simplejson.loads('{"a":1, "b":2}')
{u'a': 1, u'b': 2}
>>> eval('{"a":1, "b":2}')
{'a': 1, 'b': 2}

編輯:eval()行為不同的更好示例:

>>> simplejson.loads('{"X": "\uabcd"}')
{u'X': u'\uabcd'}
>>> eval('{"X": "\uabcd"}')
{'X': '\\uabcd'}
>>> simplejson.loads('{"X": "\uabcd"}') == eval('{"X": "\uabcd"}')
False

編輯2:看到今天SilentGhost指出的另一個問題:eval不能處理true - > True,false - > False,null - > None not correct。

>>> simplejson.loads('[false, true, null]')
[False, True, None]
>>> eval('[false, true, null]')
Traceback (most recent call last):
  File "<interactive input>", line 1, in <module>
  File "<string>", line 1, in <module>
NameError: name 'false' is not defined
>>> 

最佳實踐的觀點是,在大多數情況下,忽視它們是一個壞主意。 如果我是你,我會使用解析器將JSON解析為Python。 嘗試使用simplejson ,在我上次嘗試時解析JSON非常簡單,它聲稱與Python 2.4兼容。

我不同意谷歌不信任這一點。 我不會不信任他們,但我會核實你從他們那里得到的數據。 我實際使用JSON解析器的原因正好在你的問題中:

我自己(簡短)的研究表明,JSON恰好是完全有效的Python,除了“/”轉義序列 - GC似乎沒有生成。

是什么讓你認為Google Code永遠不會產生這樣的轉義序列?

如果使用正確的工具,解析是一個已解決的問題。 如果你試圖采用這樣的快捷方式,你最終會被錯誤的假設所困擾,或者你會做一些事情,比如當你的選擇語言已經存在解析器時,嘗試用正則表達式和布爾邏輯來破解解析器。

一個主要區別是JSON中的布爾值為true false ,但Python使用True | False

不執行此操作的最重要原因可以概括為: eval不應該用於解釋外部輸入,因為這允許任意代碼執行。

eval JSON有點像嘗試通過C ++編譯器運行XML。

eval旨在評估Python代碼。 盡管存在一些語法上的相似之處,但JSON不是Python代碼 哎呀,不僅不是Python代碼,它不是代碼開頭。 因此,即使你可以為你的用例僥幸逃脫,我也認為從概念上來說這是一個壞主意。 Python是一個蘋果,JSON是橙味的蘇打水。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM