Usage in frameworks and Zope¶
One major issue with using
compile_restricted directly in a framework is, that you have to use try-except statements to handle problems and it might be a bit harder to provide useful information to the user.
RestrictedPython provides four specialized compile_restricted methods:
Those four methods return a named tuple (
CompileResult) with four elements:
errorsis not empty
- a tuple with error messages
- a list with warnings
- a dictionary mapping collected used names to
These details can be used to inform the user about the compiled source code.
Modifying the builtins is straight forward, it is just a dictionary containing the available library elements. Modification normally means removing elements from existing builtins or adding allowed elements by copying from globals.
For frameworks it could possibly also be useful to change the handling of specific Python language elements. For that use case RestrictedPython provides the possibility to pass an own policy.
A policy is basically a special
NodeTransformer that could be instantiated with three params for
used_names, it should be a subclass of RestrictedPython.RestrictingNodeTransformer.
from RestrictedPython import compile_restricted from RestrictedPython import RestrictingNodeTransformer class OwnRestrictingNodeTransformer(RestrictingNodeTransformer): pass policy_instance = OwnRestrictingNodeTransformer( errors=, warnings=, used_names= )
compile_restricted* methods do have an optional parameter
policy, where a specific policy could be provided.
source_code = """ def do_something(): pass """ policy = OwnRestrictingNodeTransformer byte_code = compile_restricted( source_code, filename='<inline code>', mode='exec', policy=policy # policy class ) exec(byte_code, globals(), None)
One special case “unrestricted RestrictedPython” (defined to unblock ports of Zope Packages to Python 3) is to actually use RestrictedPython in an unrestricted mode, by providing a Null-Policy (aka
That special case would be written as:
from RestrictedPython import compile_restricted source_code = """ def do_something(): pass """ byte_code = compile_restricted( source_code, filename='<inline code>', mode='exec', policy=None # Null-Policy -> unrestricted ) exec(byte_code, globals(), None)