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?

+2


source to share


2 answers


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

.

+5


source


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

.

+3


source







All Articles