I am looking for a way to create a Python function from a string containing the source code at runtime, in such a way that the source code is available by inspection.
My current method looks like:
src = 'def foo(x, y):' + '\n\t' + 'return x / y'
g = {numpy: numpy, ...} # Modules and such required for function
l = {}
exec(src, g, l)
func = l['foo']
Which works perfectly fine, but the function has no source code/file associated with it. This makes debugging difficult (note the line the error occurs on in foo() isn't shown):
>>> foo(1, 0)
ZeroDivisionError Traceback (most recent call last)
<ipython-input-85-9df128c5d862> in <module>()
----> 1 myfunc(3, 0)
<string> in foo(x, y)
ZeroDivisionError: division by zero
If I define a function in the IPython interpreter, I can get the source using inspect.getsource and it will be printed in tracebacks. inspect.getsourcefile returns something like '<ipython-input-19-8efed6025c6f>' for these types of functions, which of course isn't a real file. Is there a way to do something similar in a non-interactive environment?
inspect.getsourcedoes not work for functions defined in a standard interactive session. If it seemed to work when you tried it, you may have been running IPython without realizing it.compile? . With compile You can first store the compiled code and then exec it when needed. where exec and eval makes evaluation in place without returning objects