added a pytest_helpconfig plugin which groups --version and the new "--help-config" option. rename options and configuration names. streamlines docs.

--HG--
branch : 1.0.x
This commit is contained in:
holger krekel 2009-08-19 15:45:01 +02:00
parent 30e87e887d
commit 5e4fcdd14e
21 changed files with 209 additions and 94 deletions

View File

@ -12,6 +12,10 @@ Changes between 1.0.0 and 1.0.1
* improved documentation layout and content a lot * improved documentation layout and content a lot
* added a "--help-config" option to show conftest.py / ENV-var names for
all longopt cmdline options, and some special conftest.py variables.
renamed 'conf_capture' conftest setting to 'option_capture' accordingly.
* fix issue #27: better reporting on non-collectable items given on commandline * fix issue #27: better reporting on non-collectable items given on commandline
(e.g. pyc files) (e.g. pyc files)

View File

@ -36,6 +36,7 @@ doc/test/mission.txt
doc/test/plugin/capture.txt doc/test/plugin/capture.txt
doc/test/plugin/doctest.txt doc/test/plugin/doctest.txt
doc/test/plugin/figleaf.txt doc/test/plugin/figleaf.txt
doc/test/plugin/helpconfig.txt
doc/test/plugin/hooklog.txt doc/test/plugin/hooklog.txt
doc/test/plugin/hookspec.txt doc/test/plugin/hookspec.txt
doc/test/plugin/index.txt doc/test/plugin/index.txt
@ -349,6 +350,7 @@ py/test/plugin/pytest_default.py
py/test/plugin/pytest_doctest.py py/test/plugin/pytest_doctest.py
py/test/plugin/pytest_execnetcleanup.py py/test/plugin/pytest_execnetcleanup.py
py/test/plugin/pytest_figleaf.py py/test/plugin/pytest_figleaf.py
py/test/plugin/pytest_helpconfig.py
py/test/plugin/pytest_hooklog.py py/test/plugin/pytest_hooklog.py
py/test/plugin/pytest_keyword.py py/test/plugin/pytest_keyword.py
py/test/plugin/pytest_monkeypatch.py py/test/plugin/pytest_monkeypatch.py
@ -366,6 +368,7 @@ py/test/plugin/pytest_tmpdir.py
py/test/plugin/pytest_unittest.py py/test/plugin/pytest_unittest.py
py/test/plugin/pytest_xfail.py py/test/plugin/pytest_xfail.py
py/test/plugin/test_pytest_capture.py py/test/plugin/test_pytest_capture.py
py/test/plugin/test_pytest_helpconfig.py
py/test/plugin/test_pytest_nose.py py/test/plugin/test_pytest_nose.py
py/test/plugin/test_pytest_runner.py py/test/plugin/test_pytest_runner.py
py/test/plugin/test_pytest_runner_xunit.py py/test/plugin/test_pytest_runner_xunit.py

View File

@ -1,17 +1,12 @@
1.0.1: bug fixes, nose/unittest.py support, improved reporting 1.0.1: improved reporting, nose/unittest.py support, bug fixes
-------------------------------------------------------------------- -----------------------------------------------------------------------
The py.test/pylib 1.0.1 release is a bugfix release for 1.0.1, coming The py.test/pylib 1.0.1 release is a bugfix release, coming
with improved documentation and more support for running existing with improved documentation and many test reporting improvements.
nose/unittest.py style test suites. Checkout: It also allows to run more existing nose and unittest.py style test suites.
For a testing quickstart and general documentation:
quickstart: http://codespeak.net/py/current/test/quickstart.html http://pytest.org and http://pylib.org
pytest: http://pytest.org
pylib: http://pylib.org
or read on for the changelog.
Changes 1.0.0 to 1.0.1 Changes 1.0.0 to 1.0.1
------------------------ ------------------------
@ -20,7 +15,11 @@ Changes 1.0.0 to 1.0.1
nose-style function/method/generator setup/teardown and nose-style function/method/generator setup/teardown and
tries to report functions correctly. tries to report functions correctly.
* much improved documentation layout: see http://pytest.org * improved documentation, better navigation: see http://pytest.org
* added a "--help-config" option to show conftest.py / ENV-var names for
all longopt cmdline options, and some special conftest.py variables.
renamed 'conf_capture' conftest setting to 'option_capture' accordingly.
* unicode fixes: capturing and unicode writes to sys.stdout * unicode fixes: capturing and unicode writes to sys.stdout
(through e.g a print statement) now work within tests, (through e.g a print statement) now work within tests,

View File

@ -17,85 +17,80 @@ You can see command line options by running::
py.test -h py.test -h
This will display all available command line options This will display all available command line options
including the ones added by plugins `loaded at tool startup`_. in your specific environment.
.. _`project-specific test configuration`: .. _`project-specific test configuration`:
.. _`collect_ignore`: .. _`collect_ignore`:
conftest.py: project specific test configuration conftest.py: project specific hooks and configuration
-------------------------------------------------------- --------------------------------------------------------
A unique feature of py.test are its ``conftest.py`` files which A unique feature of py.test are its ``conftest.py`` files which
allow to `set option defaults`_, `implement hooks`_, `specify funcargs`_ allow to:
* `set option defaults`_
* `implement hooks`_
* `specify funcargs`_
or set particular variables to influence the testing process: or set particular variables to influence the testing process:
* ``pytest_plugins``: list of named plugins to load * ``pytest_plugins``: list of named plugins to load
* ``collect_ignore``: list of paths to ignore during test collection (relative to the containing * ``collect_ignore``: list of paths to ignore during test collection, relative to the containing ``conftest.py`` file
``conftest.py`` file)
* ``rsyncdirs``: list of to-be-rsynced directories for distributed * ``rsyncdirs``: list of to-be-rsynced directories for distributed
testing testing, relative to the containing ``conftest.py`` file.
You may put a conftest.py files in your project root directory or into You may put a conftest.py files in your project root directory or into
your package directory if you want to add project-specific test options. your package directory if you want to add project-specific test options.
``py.test`` loads all ``conftest.py`` files upwards from the command ``py.test`` loads all ``conftest.py`` files upwards from the command
line specified test files. It will lookup configuration values line file arguments. It usually looks up configuration values
right-to-left, i.e. the closer conftest files will be checked first. right-to-left, i.e. the closer conftest files will be checked first.
You may have a ``conftest.py`` in your very home directory to have some This means you can have a ``conftest.py`` in your very home directory to
global configuration values. have some global configuration values.
There is a flag that may help you debugging your conftest.py
configuration::
py.test --traceconfig
.. _`specify funcargs`: funcargs.html#application-setup-tutorial-example .. _`specify funcargs`: funcargs.html#application-setup-tutorial-example
.. _`set option defaults`: .. _`set option defaults`:
setting option defaults setting persistent option defaults
------------------------------- ------------------------------------
py.test will lookup values of options in this order: py.test will lookup option values in this order:
* option value supplied at command line * command line
* content of environment variable ``PYTEST_OPTION_NAME=...`` * conftest.py files
* ``name = ...`` setting in the nearest ``conftest.py`` file. * environment variables
The name of an option usually is the one you find To find out about the particular switches and type::
in the longform of the option, i.e. the name
behind the ``--`` double-dash that you get with ``py.test -h``.
IOW, you can set default values for options per project, per py.test --help-config
home-directoray, per shell session or per test-run.
This will print information about all options in your
environment, including your local plugins.
.. _`basetemp`: .. _`basetemp`:
Temporary directories Temporary directories
------------------------------------------- -------------------------------------------
``py.test`` runs provide means to create per-test session You can create directories by calling one of two methods
temporary (sub) directories through the config object.
You can create directories by calling a method
on the config object: on the config object:
- ``config.mktemp(basename)``: create and returns a new tempdir - ``config.mktemp(basename)``: create and return a new tempdir
- ``config.ensuretemp(basename)``: create or return a new tempdir - ``config.ensuretemp(basename)``: create or return a new tempdir
tempdirs are created as sub directories of a per-session testdir temporary directories are created as sub directories of a per-session
and will keep around the directories of the last three testdir and will keep around the directories of the last three test
test runs. You can also set the base temporary directory runs. You can set the base temporary directory through the command line
with the `--basetemp`` option. When distributing `--basetemp`` option. When distributing tests on the same machine,
tests on the same machine, ``py.test`` takes care to ``py.test`` takes care to configure a basetemp directory for the sub
pass around the basetemp directory such that all temporary processes such that all temporary data lands below below a single
files land below the same basetemp directory. per-test run basetemp directory.
The config object is available when implementing `function arguments`_
or `extensions`_ and can otherwise be globally accessed as ``py.test.config``.
.. _`function arguments`: funcargs.html .. _`function arguments`: funcargs.html
.. _`extensions`: .. _`extensions`:

View File

@ -38,7 +38,7 @@ You can influence output capturing mechanisms from the command line::
If you set capturing values in a conftest file like this:: If you set capturing values in a conftest file like this::
# conftest.py # conftest.py
conf_capture = 'fd' option_capture = 'fd'
then all tests in that directory will execute with "fd" style capturing. then all tests in that directory will execute with "fd" style capturing.

View File

@ -0,0 +1,31 @@
pytest_helpconfig plugin
========================
provide version info, conftest/environment config names.
.. contents::
:local:
command line options
--------------------
``--help-config``
show available conftest.py and ENV-variable names.
``--version``
display py lib version and import information.
Start improving this plugin in 30 seconds
=========================================
1. Download `pytest_helpconfig.py`_ plugin source code
2. put it somewhere as ``pytest_helpconfig.py`` into your import path
3. a subsequent ``py.test`` run will use your local version
Checkout customize_, other plugins_ or `get in contact`_.
.. include:: links.txt

View File

@ -1,6 +1,6 @@
Plugins related to Python test functions and programs plugins for Python test functions
===================================================== =================================
xfail_ mark python test functions as expected-to-fail and report them separately. xfail_ mark python test functions as expected-to-fail and report them separately.
@ -13,7 +13,7 @@ capture_ configurable per-test stdout/stderr capturing mechanisms.
recwarn_ helpers for asserting deprecation and other warnings. recwarn_ helpers for asserting deprecation and other warnings.
Plugins for other testing styles and languages plugins for other testing styles and languages
============================================== ==============================================
oejskit_ run javascript tests in real life browsers oejskit_ run javascript tests in real life browsers
@ -27,7 +27,7 @@ doctest_ collect and execute doctests from modules and test files.
restdoc_ perform ReST syntax, local and remote reference tests on .rst/.txt files. restdoc_ perform ReST syntax, local and remote reference tests on .rst/.txt files.
Plugins for generic reporting and failure logging plugins for generic reporting and failure logging
================================================= =================================================
pastebin_ submit failure or test session information to a pastebin service. pastebin_ submit failure or test session information to a pastebin service.
@ -37,8 +37,20 @@ resultlog_ resultlog plugin for machine-readable logging of test results.
terminal_ Implements terminal reporting of the full testing process. terminal_ Implements terminal reporting of the full testing process.
internal plugins / core functionality plugins for generic reporting and failure logging
===================================== =================================================
pastebin_ submit failure or test session information to a pastebin service.
resultlog_ resultlog plugin for machine-readable logging of test results.
terminal_ Implements terminal reporting of the full testing process.
misc plugins / core functionality
=================================
helpconfig_ provide version info, conftest/environment config names.
pdb_ interactive debugging with the Python Debugger. pdb_ interactive debugging with the Python Debugger.

View File

@ -1,3 +1,4 @@
.. _`helpconfig`: helpconfig.html
.. _`terminal`: terminal.html .. _`terminal`: terminal.html
.. _`pytest_recwarn.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_recwarn.py .. _`pytest_recwarn.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_recwarn.py
.. _`unittest`: unittest.html .. _`unittest`: unittest.html
@ -15,6 +16,7 @@
.. _`pytest_figleaf.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_figleaf.py .. _`pytest_figleaf.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_figleaf.py
.. _`pytest_hooklog.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_hooklog.py .. _`pytest_hooklog.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_hooklog.py
.. _`checkout the py.test development version`: ../../download.html#checkout .. _`checkout the py.test development version`: ../../download.html#checkout
.. _`pytest_helpconfig.py`: http://bitbucket.org/hpk42/py-trunk/raw/1.0.1/py/test/plugin/pytest_helpconfig.py
.. _`oejskit`: oejskit.html .. _`oejskit`: oejskit.html
.. _`doctest`: doctest.html .. _`doctest`: doctest.html
.. _`get in contact`: ../../contact.html .. _`get in contact`: ../../contact.html

View File

@ -4,14 +4,16 @@ import sys
WIDTH = 75 WIDTH = 75
plugins = [ plugins = [
('Plugins related to Python test functions and programs', ('plugins for Python test functions',
'xfail figleaf monkeypatch capture recwarn',), 'xfail figleaf monkeypatch capture recwarn',),
('Plugins for other testing styles and languages', ('plugins for other testing styles and languages',
'oejskit unittest nose doctest restdoc'), 'oejskit unittest nose doctest restdoc'),
('Plugins for generic reporting and failure logging', ('plugins for generic reporting and failure logging',
'pastebin resultlog terminal',), 'pastebin resultlog terminal',),
('internal plugins / core functionality', ('plugins for generic reporting and failure logging',
'pdb keyword hooklog') 'pastebin resultlog terminal',),
('misc plugins / core functionality',
'helpconfig pdb keyword hooklog')
#('internal plugins / core functionality', #('internal plugins / core functionality',
# #'pdb keyword hooklog runner execnetcleanup # pytester', # #'pdb keyword hooklog runner execnetcleanup # pytester',
# 'pdb keyword hooklog runner execnetcleanup' # pytester', # 'pdb keyword hooklog runner execnetcleanup' # pytester',

View File

@ -64,7 +64,7 @@ class Config(object):
val = eval(val) val = eval(val)
opt.default = val opt.default = val
else: else:
name = "pytest_option_" + opt.dest name = "option_" + opt.dest
try: try:
opt.default = self._conftest.rget(name) opt.default = self._conftest.rget(name)
except (ValueError, KeyError): except (ValueError, KeyError):

View File

@ -10,6 +10,5 @@ Generator = py.test.collect.Generator
Function = py.test.collect.Function Function = py.test.collect.Function
Instance = py.test.collect.Instance Instance = py.test.collect.Instance
pytest_plugins = "default runner capture terminal keyword xfail tmpdir execnetcleanup monkeypatch recwarn pdb pastebin unittest".split() pytest_plugins = "default runner capture terminal keyword xfail tmpdir execnetcleanup monkeypatch recwarn pdb pastebin unittest helpconfig".split()
conf_capture = "fd"

View File

@ -65,7 +65,7 @@ class TestDistribution:
""", """,
) )
testdir.makeconftest(""" testdir.makeconftest("""
pytest_option_tx = 'popen popen popen'.split() option_tx = 'popen popen popen'.split()
""") """)
result = testdir.runpytest(p1, '-d') result = testdir.runpytest(p1, '-d')
result.stdout.fnmatch_lines([ result.stdout.fnmatch_lines([

View File

@ -32,7 +32,7 @@ You can influence output capturing mechanisms from the command line::
If you set capturing values in a conftest file like this:: If you set capturing values in a conftest file like this::
# conftest.py # conftest.py
conf_capture = 'fd' option_capture = 'fd'
then all tests in that directory will execute with "fd" style capturing. then all tests in that directory will execute with "fd" style capturing.
@ -131,7 +131,10 @@ class CaptureManager:
def _getmethod(self, config, fspath): def _getmethod(self, config, fspath):
if config.option.capture: if config.option.capture:
return config.option.capture return config.option.capture
return config._conftest.rget("conf_capture", path=fspath) try:
return config._conftest.rget("option_capture", path=fspath)
except KeyError:
return "fd"
def resumecapture_item(self, item): def resumecapture_item(self, item):
method = self._getmethod(item.config, item.fspath) method = self._getmethod(item.config, item.fspath)

View File

@ -61,13 +61,13 @@ def pytest_addoption(parser):
action="store", dest="tbstyle", default='long', action="store", dest="tbstyle", default='long',
type="choice", choices=['long', 'short', 'no'], type="choice", choices=['long', 'short', 'no'],
help="traceback verboseness (long/short/no).") help="traceback verboseness (long/short/no).")
group._addoption('-p', action="append", dest="plugin", default = [], group._addoption('-p', action="append", dest="plugins", default = [],
help=("load the specified plugin after command line parsing. ")) help=("load the specified plugin after command line parsing. "))
group._addoption('-f', '--looponfail', group._addoption('-f', '--looponfail',
action="store_true", dest="looponfail", default=False, action="store_true", dest="looponfail", default=False,
help="run tests, re-run failing test set until all pass.") help="run tests, re-run failing test set until all pass.")
group = parser.addgroup("test process debugging") group = parser.addgroup("debugconfig", "test process debugging and configuration")
group.addoption('--basetemp', dest="basetemp", default=None, metavar="dir", group.addoption('--basetemp', dest="basetemp", default=None, metavar="dir",
help="base temporary directory for this test run.") help="base temporary directory for this test run.")
@ -91,17 +91,10 @@ def pytest_addoption(parser):
help="shortcut for '--dist=load --tx=NUM*popen'") help="shortcut for '--dist=load --tx=NUM*popen'")
group.addoption('--rsyncdir', action="append", default=[], metavar="dir1", group.addoption('--rsyncdir', action="append", default=[], metavar="dir1",
help="add directory for rsyncing to remote tx nodes.") help="add directory for rsyncing to remote tx nodes.")
group.addoption('--version', action="store_true",
help="display version information")
def pytest_configure(config): def pytest_configure(config):
fixoptions(config) fixoptions(config)
setsession(config) setsession(config)
if config.option.version:
p = py.path.local(py.__file__).dirpath()
sys.stderr.write("This is py.test version %s, imported from %s\n" %
(py.__version__, p))
sys.exit(0)
#xxxloadplugins(config) #xxxloadplugins(config)
def fixoptions(config): def fixoptions(config):
@ -154,7 +147,7 @@ def test_plugin_specify(testdir):
def test_plugin_already_exists(testdir): def test_plugin_already_exists(testdir):
config = testdir.parseconfig("-p", "default") config = testdir.parseconfig("-p", "default")
assert config.option.plugin == ['default'] assert config.option.plugins == ['default']
config.pluginmanager.do_configure(config) config.pluginmanager.do_configure(config)

View File

@ -0,0 +1,63 @@
""" provide version info, conftest/environment config names.
"""
import py
import sys
def pytest_addoption(parser):
group = parser.getgroup('debugconfig')
group.addoption("--help-config", action="store_true", dest="helpconfig",
help="show available conftest.py and ENV-variable names.")
group.addoption('--version', action="store_true",
help="display py lib version and import information.")
def pytest_configure(__multicall__, config):
if config.option.version:
p = py.path.local(py.__file__).dirpath()
sys.stderr.write("This is py.test version %s, imported from %s\n" %
(py.__version__, p))
sys.exit(0)
if not config.option.helpconfig:
return
__multicall__.execute()
options = []
for group in config._parser._groups:
options.extend(group.options)
widths = [0] * 10
tw = py.io.TerminalWriter()
tw.sep("-")
tw.line("%-13s | %-18s | %-25s | %s" %(
"cmdline name", "conftest.py name", "ENV-variable name", "help"))
tw.sep("-")
options = [opt for opt in options if opt._long_opts]
options.sort(lambda x, y: cmp(x._long_opts, y._long_opts))
for opt in options:
if not opt._long_opts:
continue
optstrings = list(opt._long_opts) # + list(opt._short_opts)
optstrings = filter(None, optstrings)
optstring = "|".join(optstrings)
line = "%-13s | %-18s | %-25s | %s" %(
optstring,
"option_%s" % opt.dest,
"PYTEST_OPTION_%s" % opt.dest.upper(),
opt.help and opt.help or "",
)
tw.line(line[:tw.fullwidth])
for name, help in conftest_options:
line = "%-13s | %-18s | %-25s | %s" %(
"",
name,
"",
help,
)
tw.line(line[:tw.fullwidth])
tw.sep("-")
sys.exit(0)
conftest_options = (
('pytest_plugins', 'list of plugin names to load'),
('collect_ignore', '(relative) paths ignored during collection'),
('rsyncdirs', 'to-be-rsynced directories for dist-testing'),
)

View File

@ -7,7 +7,7 @@ import py
import sys import sys
def pytest_addoption(parser): def pytest_addoption(parser):
group = parser.getgroup("test process debugging") group = parser.getgroup("debugconfig")
group.addoption('--collectonly', group.addoption('--collectonly',
action="store_true", dest="collectonly", action="store_true", dest="collectonly",
help="only collect tests, don't execute them."), help="only collect tests, don't execute them."),

View File

@ -12,7 +12,7 @@ class TestCaptureManager:
for name in ('no', 'fd', 'sys'): for name in ('no', 'fd', 'sys'):
sub = testdir.tmpdir.mkdir("dir" + name) sub = testdir.tmpdir.mkdir("dir" + name)
sub.ensure("__init__.py") sub.ensure("__init__.py")
sub.join("conftest.py").write('conf_capture = %r' % name) sub.join("conftest.py").write('option_capture = %r' % name)
assert capman._getmethod(config, sub.join("test_hello.py")) == name assert capman._getmethod(config, sub.join("test_hello.py")) == name
@py.test.mark.multi(method=['no', 'fd', 'sys']) @py.test.mark.multi(method=['no', 'fd', 'sys'])

View File

@ -0,0 +1,18 @@
import py, os
def test_version(testdir):
assert py.version == py.__version__
result = testdir.runpytest("--version")
assert result.ret == 0
p = py.path.local(py.__file__).dirpath()
assert result.stderr.fnmatch_lines([
'*py.test*%s*imported from*%s*' % (py.version, p)
])
def test_helpconfig(testdir):
result = testdir.runpytest("--help-config")
assert result.ret == 0
assert result.stdout.fnmatch_lines([
"*cmdline*conftest*ENV*",
])

View File

@ -233,8 +233,7 @@ def importplugin(importspec):
def isgenerichook(name): def isgenerichook(name):
return name == "pytest_plugins" or \ return name == "pytest_plugins" or \
name.startswith("pytest_funcarg__") or \ name.startswith("pytest_funcarg__")
name.startswith("pytest_option_")
def getargs(func): def getargs(func):
args = py.std.inspect.getargs(func.func_code)[0] args = py.std.inspect.getargs(func.func_code)[0]

View File

@ -1,14 +1,6 @@
import py import py
class TestGeneralUsage: class TestGeneralUsage:
def test_version(self, testdir):
assert py.version == py.__version__
result = testdir.runpytest("--version")
assert result.ret == 0
p = py.path.local(py.__file__).dirpath()
assert result.stderr.fnmatch_lines([
'*py.test*%s*imported from*%s*' % (py.version, p)
])
def test_config_error(self, testdir): def test_config_error(self, testdir):
testdir.makeconftest(""" testdir.makeconftest("""
def pytest_configure(config): def pytest_configure(config):

View File

@ -42,7 +42,7 @@ class TestConfigCmdlineParsing:
def test_parser_addoption_default_conftest(self, testdir, monkeypatch): def test_parser_addoption_default_conftest(self, testdir, monkeypatch):
import os import os
testdir.makeconftest("pytest_option_verbose=True") testdir.makeconftest("option_verbose=True")
config = testdir.parseconfig() config = testdir.parseconfig()
assert config.option.verbose assert config.option.verbose