В python 2.7 я мог бы ограничить пространство имен __builtins__
, используемое eval, определяя глобальный как {'__builtins__': None}
. Это не работает в Python 3.5.Как правильно ограничить __builtins__ в eval в Python 3.5?
Python 2.7 правильно дает NameError:
In [1]: eval('round', {'__builtins__': None})
---------------------------------------------------------------------------
NameError Traceback (most recent call last)
<ipython-input-14-dc1cae9c6b26> in <module>()
----> 1 eval('round', {'__builtins__': None})
<string> in <module>()
NameError: name 'round' is not defined
Python 3.5 дает следующее:
In [1]: eval('round', {'__builtins__': None})
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-9-83a8846287f1> in <module>()
----> 1 eval('round', {'__builtins__': None})
<string> in <module>()
TypeError: 'NoneType' object is not subscriptable
Оба дают правильный выход для следующего:
In [1]: eval('round')
Out[1]: <function round>
Как я должным образом ограничить __builtins__
или обойти это?
Отлично, спасибо. Есть ли другой способ оценки математических операций, например. '1 + 1'? AFIK, 'ast.literal_eval' этого не допускает. – mrclary
Другие компоненты в 'ast' достаточно сильны, чтобы создать парсер для любого подмножества нужного вам языка ... но это может быть значительная работа, и вам нужно быть очень осторожным в разрешении доступа к атрибутам (т. Е. 'foo.bar' точечный синтаксис). – Kevin