Welcome to Hunter’s documentation!¶
Contents:
Overview¶
Hunter¶
docs | |
---|---|
tests | |
package |
Hunter is a flexible code tracing toolkit, not for measuring coverage, but for debugging, logging, inspection and other nefarious purposes. It has a simple Python API and a convenient terminal API (see Environment variable activation).
API is considered unstable until 1.0 is released.
- Free software: BSD license
Installation¶
pip install hunter
Documentation¶
Overview¶
The default action is to just print the code being executed. Example:
import hunter
hunter.trace(module='posixpath')
import os
os.path.join('a', 'b')
Would result in:
python2.7/posixpath.py:60 call def join(a, *p):
python2.7/posixpath.py:64 line path = a
python2.7/posixpath.py:65 line for b in p:
python2.7/posixpath.py:66 line if b.startswith('/'):
python2.7/posixpath.py:68 line elif path == '' or path.endswith('/'):
python2.7/posixpath.py:71 line path += '/' + b
python2.7/posixpath.py:65 line for b in p:
python2.7/posixpath.py:72 line return path
python2.7/posixpath.py:72 return return path
... return value: 'a/b'
- or in a terminal:

You can have custom actions, like a variable printer - example:
import hunter
hunter.trace(hunter.Q(module='posixpath', action=hunter.VarsPrinter('path')))
import os
os.path.join('a', 'b')
Would result in:
python2.7/posixpath.py:60 call def join(a, *p):
python2.7/posixpath.py:64 line path = a
vars path => 'a'
python2.7/posixpath.py:65 line for b in p:
vars path => 'a'
python2.7/posixpath.py:66 line if b.startswith('/'):
vars path => 'a'
python2.7/posixpath.py:68 line elif path == '' or path.endswith('/'):
vars path => 'a'
python2.7/posixpath.py:71 line path += '/' + b
vars path => 'a/b'
python2.7/posixpath.py:65 line for b in p:
vars path => 'a/b'
python2.7/posixpath.py:72 line return path
vars path => 'a/b'
python2.7/posixpath.py:72 return return path
... return value: 'a/b'
- or in a terminal:

You can give it a tree-like configuration where you can optionally configure specific actions for parts of the tree (like dumping variables or a pdb set_trace):
TODO: More examples.
Environment variable activation¶
For your convenience environment variable activation is available. Just run your app like this:
PYTHONHUNTER="module='os.path'" python yourapp.py
On Windows you’d do something like:
set PYTHONHUNTER=module='os.path'
python yourapp.py
The activation works with a clever .pth
file that checks for that env var presence and before your app runs does something like this:
from hunter import *
trace(<whatever-you-had-in-the-PYTHONHUNTER-env-var>)
That also means that it will do activation even if the env var is empty, eg: PYTHONHUNTER=""
.
Introduction¶
The trace
function¶
The hunter.trace
function can take 2 types of arguments:
- Keyword arguments like
module
,function
oraction
. This is for convenience. - Callbacks that take an
event
argument:- Builtin predicates like:
hunter.Query
,hunter.When
,hunter.And
orhunter.Or
. - Actions like:
hunter.CodePrinter
,hunter.Debugger
orhunter.VarsPrinter
- Builtin predicates like:
Note that hunter.trace
will use hunter.Q
when you pass multiple positional arguments or keyword arguments.
The Q
function¶
The hunter.Q
function provides a convenience API for you:
Q(module='foobar')
is converted toQuery(module='foobar')
.Q(module='foobar', action=Debugger)
is converted toWhen(Query(module='foobar'), Debugger)
.Q(module='foobar', actions=[CodePrinter, VarsPrinter('name')])
is converted toWhen(Query(module='foobar'), CodePrinter, VarsPrinter('name'))
.Q(Q(module='foo'), Q(module='bar'))
is converted toOr(Q(module='foo'), Q(module='bar'))
.Q(your_own_callback, module='foo')
is converted toOr(your_own_callback, Q(module='foo'))
.
The builtin predicates and actions¶
All the builtin predicates (hunter.Query
, hunter.When
, hunter.And
and hunter.Or
) support the |
and &
operators:
Query(module='foo') | Query(module='bar')
is converted toOr(Query(module='foo'), Query(module='bar'))
Query(module='foo') & Query(module='bar')
is converted toAnd(Query(module='foo'), Query(module='bar'))
Activation¶
You can activate Hunter in two ways.
via code¶
import hunter
hunter.trace(
...
)
via environment variable¶
Set the PYTHONHUNTER
environment variable. Eg:
PYTHONHUNTER="module='os.path'" python yourapp.py
On Windows you’d do something like:
set PYTHONHUNTER=module='os.path'
python yourapp.py
The activation works with a clever .pth
file that checks for that env var presence and before your app runs does something like this:
from hunter import *
trace(
<whatever-you-had-in-the-PYTHONHUNTER-env-var>
)
That also means that it will do activation even if the env var is empty, eg: PYTHONHUNTER=""
.
Cookbook¶
TODO
Reference¶
hunter¶
Functions
hunter.trace |
Starts tracing. |
hunter.stop |
Stop tracing. |
hunter.Q |
Handles situations where hunter.Query objects (or other callables) are passed in as positional arguments. |
Predicates
hunter.Query |
A query class. |
hunter.When |
Runs actions when condition(event) is True . |
hunter.And |
And predicate. Exits at the first sub-predicate that returns False . |
hunter.Or |
Or predicate. Exits at first sub-predicate that returns True . |
Actions
hunter.CodePrinter |
An action that just prints the code being executed. |
hunter.Debugger |
An action that starts pdb . |
hunter.VarsPrinter |
An action that prints local variables and optionally global variables visible from the current executing frame. |
Objects
hunter.Event |
Event wrapper for frame, kind, arg (the arguments the settrace function gets). |
-
hunter.
trace
(*predicates, **options)¶ Starts tracing. Can be used as a context manager (with slightly incorrect semantics - it starts tracing before
__enter__
is called).Parameters:
-
hunter.
stop
()¶ Stop tracing. Restores previous tracer (if any).
-
class
hunter.
Q
[source]¶ Handles situations where
hunter.Query
objects (or other callables) are passed in as positional arguments. Conveniently converts that to anhunter.Or
predicate.
-
class
hunter.
Query
(**query)[source]¶ A query class.
See
hunter.Event
for fields that can be filtered on.
-
class
hunter.
When
(condition, *actions)[source]¶ Runs
actions
whencondition(event)
isTrue
.Actions take a single
event
argument.
-
class
hunter.
And
(*predicates)[source]¶ And predicate. Exits at the first sub-predicate that returns
False
.
-
class
hunter.
CodePrinter
(stream=<open file '<stderr>', mode 'w'>, force_colors=False, filename_alignment=40)[source]¶ An action that just prints the code being executed.
Parameters: - stream (file-like) – Stream to write to. Default:
sys.stderr
. - filename_alignment (int) – Default size for the filename column (files are right-aligned). Default:
40
.
- stream (file-like) – Stream to write to. Default:
-
class
hunter.
VarsPrinter
(*names, **options)[source]¶ An action that prints local variables and optionally global variables visible from the current executing frame.
Parameters: - *names (strings) – Names to evaluate. Expressions can be used (will only try to evaluate if all the variables are present on the frame.
- stream (file-like) – Stream to write to. Default:
sys.stderr
. - filename_alignment (int) – Default size for the filaneme column (files are right-aligned). Default:
40
. - globals (bool) – Allow access to globals. Default:
False
(only looks at locals).
-
class
hunter.
Event
(frame, kind, arg, tracer)[source]¶ Event wrapper for
frame, kind, arg
(the arguments the settrace function gets).Provides few convenience properties.
-
fullsource
[source]¶ A string with the sourcecode for the current statement (from
linecache
- failures are ignored).May include multiple lines if it’s a class/function definition (will include decorators).
-
Contributing¶
Contributions are welcome, and they are greatly appreciated! Every little bit helps, and credit will always be given.
Bug reports¶
When reporting a bug please include:
- Your operating system name and version.
- Any details about your local setup that might be helpful in troubleshooting.
- Detailed steps to reproduce the bug.
Documentation improvements¶
Hunter could always use more documentation, whether as part of the official Hunter docs, in docstrings, or even on the web in blog posts, articles, and such.
Feature requests and feedback¶
The best way to send feedback is to file an issue at https://github.com/ionelmc/python-hunter/issues.
If you are proposing a feature:
- Explain in detail how it would work.
- Keep the scope as narrow as possible, to make it easier to implement.
- Remember that this is a volunteer-driven project, and that contributions are welcome :)
Development¶
To set up python-hunter for local development:
Clone your fork locally:
git clone git@github.com:your_name_here/python-hunter.git
Create a branch for local development:
git checkout -b name-of-your-bugfix-or-feature
Now you can make your changes locally.
When you’re done making changes, run all the checks, doc builder and spell checker with tox one command:
tox
Commit your changes and push your branch to GitHub:
git add . git commit -m "Your detailed description of your changes." git push origin name-of-your-bugfix-or-feature
Submit a pull request through the GitHub website.
Pull Request Guidelines¶
If you need some code review or feedback while you’re developing the code just make the pull request.
For merging, you should:
- Include passing tests (run
tox
) [1]. - Update documentation when there’s new API, functionality etc.
- Add a note to
CHANGELOG.rst
about the changes. - Add yourself to
AUTHORS.rst
.
[1] | If you don’t have all the necessary python versions available locally you can rely on Travis - it will run the tests for each change you add in the pull request. It will be slower though ... |
Tips¶
To run a subset of tests:
tox -e envname -- py.test -k test_myfeature
To run all the test environments in parallel (you need to pip install detox
):
detox
Authors¶
- Ionel Cristian Mărieș - http://blog.ionelmc.ro
Changelog¶
0.6.0 (2015-10-10)¶
- Added a
clear_env_var
option on the tracer (disables tracing in subprocess). - Added
force_colors
option onVarsPrinter
andCodePrinter
. - Allowed setting the stream to a file name (option on
VarsPrinter
andCodePrinter
). - Bumped up the filename alignment to 40 cols.
- If not merging then self is not kept as a previous tracer anymore. Closes #16.
- Fixed handling in VarsPrinter: properly print eval errors and don’t try to show anything if there’s an AttributeError. Closes #18.
- Added a
stdlib
boolean flag (for filtering purposes). Closes #15. - Fixed broken frames that have “None” for filename or module (so they can still be treated as strings).
- Corrected output files in the
install_lib
command so that pip can uninstall the pth file. This only works when it’s installed with pip (sadly,setup.py install/develop
andpip install -e
will still leave pth garbage onpip uninstall hunter
).
0.5.1 (2015-04-15)¶
- Fixed
Event.globals
to actually be the dict of global vars (it was just the locals).
0.5.0 (2015-04-06)¶
- Fixed
And
andOr
“single argument unwrapping”. - Implemented predicate compression. Example:
Or(Or(a, b), c)
is converted toOr(a, b, c)
. - Renamed the
Event.source
toEvent.fullsource
. - Added
Event.source
that doesn’t do any fancy sourcecode tokenization. - Fixed
Event.fullsource
return value for situations where the tokenizer would fail. - Made the print function available in the
PYTHONHUNTER
env var payload. - Added a __repr__ for
Event
.
0.4.0 (2015-03-29)¶
- Disabled colors for Jython (contributed by Claudiu Popa in #12).
- Test suite fixes for Windows (contributed by Claudiu Popa in #11).
- Added an introduction section in the docs.
- Implemented a prettier fallback for when no sources are available for that frame.
- Implemented fixups in cases where you use action classes as a predicates.
0.3.1 (2015-03-29)¶
- Forgot to merge some commits ...
0.3.0 (2015-03-29)¶
- Added handling for internal repr failures.
- Fixed issues with displaying code that has non-ascii characters.
- Implemented better display for
call
frames so that when a function has decorators the function definition is shown (instead of just the first decorator). See: #8.
0.2.1 (2015-03-28)¶
- Added missing color entry for exception events.
- Added
Event.line
property. It returns the source code for the line being run.
0.2.0 (2015-03-27)¶
- Added color support (and
colorama
as dependency). - Added support for expressions in
VarsPrinter
. - Breaking changes:
- Renamed
F
toQ
. AndQ
is now just a convenience wrapper forQuery
. - Renamed the
PYTHON_HUNTER
env variable toPYTHONHUNTER
. - Changed
When
to take positional arguments. - Changed output to show 2 path components (still not configurable).
- Changed
VarsPrinter
to take positional arguments for the names.
- Renamed
- Improved error reporting for env variable activation (
PYTHONHUNTER
). - Fixed env var activator (the
.pth
file) installation withsetup.py install
(the “egg installs”) andsetup.py develop
/pip install -e
(the “egg links”).
0.1.0 (2015-03-22)¶
- First release on PyPI.