Python 中更安全的 eval


問題

想要將一段列表形式的字符串轉為 list,但是擔心這個動態的字符串可能是惡意的代碼?使用 eval 將帶來安全隱患。比如:

# 期望是
eval('[1, 2, 3]')

# 實際上是
eval("os.popen('rm -rf *')")

解決方案

使用 ast.literal_eval 可以很好的避免這個問題,該函數可以安全執行僅包含文字的表達式字符串。支持的對象有字符串、字節、數字、元組、列表、字典、集合、 布爾值、NoneEllipsis。這些是可以嵌套的,比如以字典作為元素的列表:

>>> from ast import literal_eval
>>> literal_eval("[{'name': 'john', 'location': 'halo7'}]")
[{'name': 'john', 'location': 'halo7'}]

注意 literal_eval 不可以執行任何復雜的表達式,比如包含運算符或是有索引的表達式都是不支持的,會直接拋出異常。這也保證了它不會執行惡意代碼。

拓展

  • 使用 literal_eval 時,足夠復雜或是巨大的字符串可能導致 Python 解釋器的崩潰,因為 Python 的 AST 編譯器是有棧深限制的
  • literal_eval 解析異常時,可能會拋出 ValueError, TypeError, SyntaxError, MemoryErrorRecursionError,這取決於傳入的字符串


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM