问题
Interrupting execution of python code with
import ipdb; ipdb.set_trace()
sometimes (but not always) drops me into ipdb without showing surrounding lines of code, even if I issue the l
command. Ie, I get something like
> /path/to/file.py(58)main()
ipdb>
instead of
> /path/to/file.py(58)main()
-> print('hello 2')
55 print('hello')
56 import pdb; pdb.set_trace()
57
58 -> print('hello 2')
59 print('hello 3')
ipdb>
Does anyone know how to show lines of code?
Edit: If I s
tep into a new function (situated in another file), a single surrounding line each side does appear.
回答1:
ipdb
is a wrapper around the stock python debugger pdb so in those cases where ipdb
can't show line numbers neither will pdb
be able to do so.
pdb
gets its source text from python module linecache. And there are various things that can foil it. The most obvious case is when there is no source file.
This happens if you are evaluating a string. For example maybe are in the middle of eval("x+1")
or exec("z=1+2")
.
Along those same lines, you might have defined function via exec
and you are now in the middle of running that function. For example:
exec("def five(): return 5")
five()
The way you may be able to tell that you are in this kind of case is to adjust the stack frame and look at the calling context. So when that happens, run up
or bt
(backtrace):
If you see:
(Pdb) up
> <string>(1)<module>()
The <string>
thing means that you are in this situation. A backtrace may show something like:
/usr/lib/python2.7/bdb.py(400)run()
-> exec cmd in globals, locals
> <string>(1)<module>()
Other ways where the source might not exist may be that the source code was deleted, or maybe the bytecode was generated all by itself, or via an AST.
There is another debugger for Python called trepan (for Python 3 see trepan3k) that tries a lot harder to find the source text. And it also tries to verify that the source code it shows matches what the Python interpreter is running by using more than just the basename part of the filename.
The debugger can even reconstruct the Python source code when there is none! This magic is done via uncompyle6.
So show this, here is an example for this simple Python program:
x = 3
eval("x+1")
exec("z=2")
Now we run the debugger:
$ trepan3k /tmp/foo.py
(/tmp/foo.py:1): <module>
-> 1 x = 3
(trepan3k) step
(/tmp/foo.py:2 @6): <module>
-- 2 eval("x+1")
(trepan3k) step
(<string>:1): <module>
(/tmp/foo.py:2 @12): <module>
-> 2 eval("x+1")
(trepan3k) list
** No file <string> found
(trepan3k) deparse .
return x + 1
(trepan3k) step
(<string>:1 @7): <module>
(/tmp/foo.py:2 @12): <module>
<- 2 eval("x+1")
R=> 4
(trepan3k) step
(/tmp/foo.py:3 @16): <module>
-- 3 exec("z=2")
(trepan3k) list
End position changed to last line 3
1 x = 3
2 eval("x+1")
3 -> exec("z=2")
(trepan3k) step
(<string>:1): <module>
(/tmp/foo.py:3 @22): <module>
-> 3 exec("z=2")
(trepan3k) list
** No file <string> found
(trepan3k) deparse .
z = 2
If this isn't enough, you can also disassemble the code to see that. And if you happen to know where the python source file is but for some reason the debugger can't find it on its own, you can tell it where the source code lives using set substitute.
来源:https://stackoverflow.com/questions/34648163/python-ipdb-occasionally-shows-no-code-lines