How can I interactively debug exceptions in Python using something besides IDLE?
Asked Answered
P

6

6

When I'm using IDLE to run a script, if the script encounters an exception and execution stops, then I'm left with a interactive shell, which I can use to investigate the application state at the time of the exception. This is really nice, but otherwise I find IDLE lacking as an editor. Is there a way I can get this "drop to interactive shell on exceptions" behavior without using IDLE?enter image description here

Pseudohermaphrodite answered 20/3, 2012 at 16:10 Comment(0)
D
4

Run your script as follows:

python -m pdb myscript.py

The console will show you:

> /home/user/dir/myscript.py(2)<module>()

-> first_line(of_my_script) (Pdb)

Type continue

Wait for things to explode:

TypeError: invalid type comparison
Uncaught exception. Entering post mortem debugging
Running 'cont' or 'step' will restart the program
> /home/user/problemscript.py(567)na_op()
-> raise TypeError("invalid type comparison")
(Pdb)

From here on out, you're basically in a MUD and a surprising number of the standard commands apply.

Type where or w to see where you are on the stack:

(Pdb) w
-> return df[df['type']=='dev'][['Dist','Count']].as_matrix()
  /home/user/core/ops.py(603)wrapper()
-> res = na_op(values, other)
> /home/user/core/ops.py(567)na_op()
-> raise TypeError("invalid type comparison")

See that little > arrow? That's where we are in the stack.

Use list or l to look around:

(Pdb) list
564               try:
565                   result = getattr(x, name)(y)
566                   if result is NotImplemented:
567  >>                     raise TypeError("invalid type comparison")
568               except (AttributeError):
569  ->                 result = op(x, y)
570   
571           return result
572   
573       def wrapper(self, other):
574           if isinstance(other, pd.Series):

To move around in the stack continue MUDing and use up (u) or down (d).

Use args (a) to examine what arguments the current function was called with:

(Pdb) args
dat = array([], shape=(0, 3), dtype=float64)
dev_classes = {81, 82, 21, 22, 23, 24, 31}

Use p to print out the contents of a variable (or pp to pretty-print (or handle your character's basic needs)):

(Pdb) p df
Empty DataFrame
Columns: [Dist, type, Count]
Index: []

Use interact to enter the code at the current point in the stack. Ctrl+D brings you back in to PDB.

Go forth! It will take many brave and mighty adventurers to turn back the assembled goblin hordes, now surrounding the city. Will you be the one to defeat the Goblin King, to reclaim the land for the races?

Dredger answered 5/3, 2015 at 22:49 Comment(0)
F
6

I suggest using eclipse with pydev. It has many debug options, I dont see any advantage in using a shell for debugging. Try it and you may, I say.

Fulk answered 20/3, 2012 at 16:16 Comment(0)
D
4

Run your script as follows:

python -m pdb myscript.py

The console will show you:

> /home/user/dir/myscript.py(2)<module>()

-> first_line(of_my_script) (Pdb)

Type continue

Wait for things to explode:

TypeError: invalid type comparison
Uncaught exception. Entering post mortem debugging
Running 'cont' or 'step' will restart the program
> /home/user/problemscript.py(567)na_op()
-> raise TypeError("invalid type comparison")
(Pdb)

From here on out, you're basically in a MUD and a surprising number of the standard commands apply.

Type where or w to see where you are on the stack:

(Pdb) w
-> return df[df['type']=='dev'][['Dist','Count']].as_matrix()
  /home/user/core/ops.py(603)wrapper()
-> res = na_op(values, other)
> /home/user/core/ops.py(567)na_op()
-> raise TypeError("invalid type comparison")

See that little > arrow? That's where we are in the stack.

Use list or l to look around:

(Pdb) list
564               try:
565                   result = getattr(x, name)(y)
566                   if result is NotImplemented:
567  >>                     raise TypeError("invalid type comparison")
568               except (AttributeError):
569  ->                 result = op(x, y)
570   
571           return result
572   
573       def wrapper(self, other):
574           if isinstance(other, pd.Series):

To move around in the stack continue MUDing and use up (u) or down (d).

Use args (a) to examine what arguments the current function was called with:

(Pdb) args
dat = array([], shape=(0, 3), dtype=float64)
dev_classes = {81, 82, 21, 22, 23, 24, 31}

Use p to print out the contents of a variable (or pp to pretty-print (or handle your character's basic needs)):

(Pdb) p df
Empty DataFrame
Columns: [Dist, type, Count]
Index: []

Use interact to enter the code at the current point in the stack. Ctrl+D brings you back in to PDB.

Go forth! It will take many brave and mighty adventurers to turn back the assembled goblin hordes, now surrounding the city. Will you be the one to defeat the Goblin King, to reclaim the land for the races?

Dredger answered 5/3, 2015 at 22:49 Comment(0)
R
3

python -i yourscript will drop to an interactive shell when yourscript exits. At this point you can run:

>>> import pdb
>>> pdb.pm()

...and get an interactive debugging shell.

See the PDB documentation.

Rattray answered 20/3, 2012 at 16:13 Comment(0)
H
3

You can use the pdb module.

import pdb
try:
    i = 0
    i = i + 'a string'
except Exception, err:
    pdb.set_trace()
Heretic answered 20/3, 2012 at 16:14 Comment(1)
That would be the case. I use it for smaller parts, where I assume something could go wrong. If you don't like that, go with Charles Duffs proposal.Heretic
C
1

IMHO, If you are working in python and not using IPython you are wasting your time (in the literal sense).

In it, you can turn pdb on or off by just typeing the "magic" command pdb. The new qtconsole (my favorite) and notebook options make this killer environment even better.

Chen answered 20/3, 2012 at 16:32 Comment(1)
Is IPython an IDE? Or is it only for interactive stuff?Pseudohermaphrodite
A
1

Run your script from inside the python command interpreter (import it), and when there is an exception do import pdb; pdb.pm() to get a debugger at the point after the exception was raised.

Average answered 20/3, 2012 at 16:35 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.