Can't get the source code for a method declared via exec using validation in Python
The following code throws an exception:
import inspect
def work():
my_function_code = """def print_hello():
print('Hi!')
"""
exec(my_function_code, globals())
inspect.getsource(print_hello)
The above code throws an IOError exception. If I declare a function without using exec (as shown below), I can get its source code just fine.
import inspect
def work():
def print_hello():
print('Hi!')
inspect.getsource(print_hello)
I have a good reason to do something like this.
Is there a workaround for this? Can you do something like this? If not, why not?
I just looked at inspect.py after reading @jsbueno's answer, this is what I found:
def findsource(object):
"""Return the entire source file and starting line number for an object.
The argument may be a module, class, method, function, traceback, frame,
or code object. The source code is returned as a list of all the lines
in the file and the line number indexes a line in that list. An **IOError
is raised if the source code cannot be retrieved.**"""
try:
file = open(getsourcefile(object))
except (TypeError, IOError):
raise IOError, 'could not get source code'
lines = file.readlines() #reads the file
file.close()
It clearly states that it is trying to open the original file and then reads its contents, so this is not possible in the case exec
.
It's not even possible. What python does to get to the source of any executable code is download the source file - to disk. It finds this file by looking at the attribute __file__
in the code module.
The line used to create a code object via "exec" or "compiled" is not supported by objects resulting from these calls.
You can probably take a look at the code if you set a variable __file__
in the global dictionary of your generated code and write the original string to that file before calling inspect.getsource
.