Skip to content

Commit f7b5bb2

Browse files
committed
Merged branch features into features
2 parents 32ca5cd + 7927dff commit f7b5bb2

35 files changed

+536
-535
lines changed

AUTHORS

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,7 @@ Samuele Pedroni
100100
Steffen Allner
101101
Stephan Obermann
102102
Tareq Alayan
103+
Ted Xiao
103104
Simon Gomizelj
104105
Stefano Taschini
105106
Stefan Farmbauer
@@ -109,3 +110,4 @@ Trevor Bekolay
109110
Vasily Kuznetsov
110111
Wouter van Ackooy
111112
Bernard Pratz
113+
Stefan Zimmermann

CHANGELOG.rst

Lines changed: 63 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,40 @@
1+
3.0.0.dev1
2+
==========
3+
4+
**Changes**
5+
6+
*
7+
8+
*
9+
10+
*
11+
12+
* Fix (`#607`_): pytest.skip() is no longer allowed at module level to
13+
prevent misleading use as test function decorator. When used at a module
14+
level an error will be raised during collection.
15+
Thanks `@omarkohl`_ for the complete PR (`#1519`_).
16+
17+
*
18+
19+
**Incompatible changes**
20+
21+
* Removing the following deprecated commandline options
22+
23+
* ``--genscript``
24+
* ``--no-assert``
25+
* ``--nomagic``
26+
* ``--report``
27+
28+
Thanks to `@RedBeardCode`_ for the PR(`#1664`_)
29+
30+
* removed support code for python 3 < 3.3 addressing (`#1627`_)
31+
32+
.. _#607: https://github.com/pytest-dev/pytest/issues/607
33+
.. _#1519: https://github.com/pytest-dev/pytest/pull/1519
34+
.. _#1664: https://github.com/pytest-dev/pytest/pull/1664
35+
.. _#1627: https://github.com/pytest-dev/pytest/pull/1627
36+
37+
138
2.10.0.dev1
239
===========
340

@@ -58,6 +95,19 @@
5895
finalizer and has access to the fixture's result cache.
5996
Thanks `@d6e`_, `@sallner`_
6097

98+
* Issue a warning for asserts whose test is a tuple literal. Such asserts will
99+
never fail because tuples are always truthy and are usually a mistake
100+
(see `#1562`_). Thanks `@kvas-it`_, for the PR.
101+
102+
* New cli flag ``--override-ini`` or ``-o`` that overrides values from the ini file.
103+
Example '-o xfail_strict=True'. A complete ini-options can be viewed
104+
by py.test --help. Thanks `@blueyed`_ and `@fengxx`_ for the PR
105+
106+
* Remove all py.test-X* entry points. The versioned, suffixed entry points
107+
were never documented and a leftover from a pre-virtualenv era. These entry
108+
points also created broken entry points in wheels, so removing them also
109+
removes a source of confusion for users (`#1632`_).
110+
Thanks `@obestwalter`_ for the PR.
61111

62112
**Changes**
63113

@@ -118,8 +168,11 @@
118168
Thanks `@Vogtinator`_ for reporting. Thanks to `@RedBeardCode`_ and
119169
`@tomviner`_ for PR.
120170

121-
*
171+
* Add proposal to docs for a new feature that enables users to combine multiple
172+
fixtures into one. Thanks to `@hpk42`_ and `@hackebrot`_.
173+
122174

175+
.. _#1632: https://github.com/pytest-dev/pytest/issues/1632
123176
.. _#1580: https://github.com/pytest-dev/pytest/pull/1580
124177
.. _#1605: https://github.com/pytest-dev/pytest/issues/1605
125178
.. _#1597: https://github.com/pytest-dev/pytest/pull/1597
@@ -131,6 +184,8 @@
131184
.. _@nikratio: https://github.com/nikratio
132185
.. _@RedBeardCode: https://github.com/RedBeardCode
133186
.. _@Vogtinator: https://github.com/Vogtinator
187+
.. _@blueyed: https://github.com/blueyed
188+
.. _@fengxx: https://github.com/fengxx
134189

135190
* Fix `#1421`_: Exit tests if a collection error occurs and add
136191
``--continue-on-collection-errors`` option to restore previous behaviour.
@@ -139,6 +194,11 @@
139194

140195
*
141196

197+
* ``OptionGroup.addoption()`` now checks if option names were already
198+
added before, to make it easier to track down issues like `#1618`_.
199+
Before, you only got exceptions later from ``argparse`` library,
200+
giving no clue about the actual reason for double-added options.
201+
142202
.. _@milliams: https://github.com/milliams
143203
.. _@csaftoiu: https://github.com/csaftoiu
144204
.. _@flub: https://github.com/flub
@@ -172,10 +232,12 @@
172232
.. _#1619: https://github.com/pytest-dev/pytest/issues/1619
173233
.. _#372: https://github.com/pytest-dev/pytest/issues/372
174234
.. _#1544: https://github.com/pytest-dev/pytest/issues/1544
235+
.. _#1562: https://github.com/pytest-dev/pytest/issues/1562
175236
.. _#1616: https://github.com/pytest-dev/pytest/pull/1616
176237
.. _#1628: https://github.com/pytest-dev/pytest/pull/1628
177238
.. _#1629: https://github.com/pytest-dev/pytest/issues/1629
178239
.. _#1633: https://github.com/pytest-dev/pytest/pull/1633
240+
.. _#1618: https://github.com/pytest-dev/pytest/issues/1618
179241

180242

181243
**Bug Fixes**

README.rst

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
:target: https://ci.appveyor.com/project/pytestbot/pytest
1818

1919
The ``pytest`` framework makes it easy to write small tests, yet
20-
scales to support complex functional testing for applications and libraries.
20+
scales to support complex functional testing for applications and libraries.
2121

2222
An example of a simple test:
2323

@@ -35,7 +35,7 @@ To execute it::
3535

3636
$ pytest
3737
======= test session starts ========
38-
platform linux -- Python 3.4.3, pytest-2.8.5, py-1.4.31, pluggy-0.3.1
38+
platform linux -- Python 3.4.3, pytest-2.8.5, py-1.4.31, pluggy-0.3.1
3939
collected 1 items
4040

4141
test_sample.py F
@@ -52,7 +52,7 @@ To execute it::
5252
======= 1 failed in 0.12 seconds ========
5353

5454
Due to ``pytest``'s detailed assertion introspection, only plain ``assert`` statements are used. See `getting-started <http://pytest.org/latest/getting-started.html#our-first-test-run>`_ for more examples.
55-
55+
5656

5757
Features
5858
--------
@@ -69,7 +69,7 @@ Features
6969
- Can run `unittest <http://pytest.org/latest/unittest.html>`_ (or trial),
7070
`nose <http://pytest.org/latest/nose.html>`_ test suites out of the box;
7171

72-
- Python2.6+, Python3.2+, PyPy-2.3, Jython-2.5 (untested);
72+
- Python2.6+, Python3.3+, PyPy-2.3, Jython-2.5 (untested);
7373

7474
- Rich plugin architecture, with over 150+ `external plugins <http://pytest.org/latest/plugins.html#installing-external-plugins-searching>`_ and thriving community;
7575

_pytest/assertion/__init__.py

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -25,15 +25,6 @@ def pytest_addoption(parser):
2525
'rewrite' (the default) rewrites assert
2626
statements in test modules on import to
2727
provide assert expression information. """)
28-
group.addoption('--no-assert',
29-
action="store_true",
30-
default=False,
31-
dest="noassert",
32-
help="DEPRECATED equivalent to --assert=plain")
33-
group.addoption('--nomagic', '--no-magic',
34-
action="store_true",
35-
default=False,
36-
help="DEPRECATED equivalent to --assert=plain")
3728

3829

3930
class AssertionState:
@@ -48,10 +39,6 @@ def __init__(self, config, mode):
4839
def pytest_load_initial_conftests(early_config, parser, args):
4940
ns, ns_unknown_args = parser.parse_known_and_unknown_args(args)
5041
mode = ns.assertmode
51-
no_assert = ns.noassert
52-
no_magic = ns.nomagic
53-
if no_assert or no_magic:
54-
mode = "plain"
5542
if mode == "rewrite":
5643
try:
5744
import ast # noqa

_pytest/assertion/rewrite.py

Lines changed: 15 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -125,7 +125,7 @@ def find_module(self, name, path=None):
125125
co = _read_pyc(fn_pypath, pyc, state.trace)
126126
if co is None:
127127
state.trace("rewriting %r" % (fn,))
128-
source_stat, co = _rewrite_test(state, fn_pypath)
128+
source_stat, co = _rewrite_test(self.config, fn_pypath)
129129
if co is None:
130130
# Probably a SyntaxError in the test.
131131
return None
@@ -252,8 +252,9 @@ def _write_pyc(state, co, source_stat, pyc):
252252
cookie_re = re.compile(r"^[ \t\f]*#.*coding[:=][ \t]*[-\w.]+")
253253
BOM_UTF8 = '\xef\xbb\xbf'
254254

255-
def _rewrite_test(state, fn):
255+
def _rewrite_test(config, fn):
256256
"""Try to read and rewrite *fn* and return the code object."""
257+
state = config._assertstate
257258
try:
258259
stat = fn.stat()
259260
source = fn.read("rb")
@@ -298,7 +299,7 @@ def _rewrite_test(state, fn):
298299
# Let this pop up again in the real import.
299300
state.trace("failed to parse: %r" % (fn,))
300301
return None, None
301-
rewrite_asserts(tree)
302+
rewrite_asserts(tree, fn, config)
302303
try:
303304
co = compile(tree, fn.strpath, "exec")
304305
except SyntaxError:
@@ -354,9 +355,9 @@ def _read_pyc(source, pyc, trace=lambda x: None):
354355
return co
355356

356357

357-
def rewrite_asserts(mod):
358+
def rewrite_asserts(mod, module_path=None, config=None):
358359
"""Rewrite the assert statements in mod."""
359-
AssertionRewriter().run(mod)
360+
AssertionRewriter(module_path, config).run(mod)
360361

361362

362363
def _saferepr(obj):
@@ -543,6 +544,11 @@ class AssertionRewriter(ast.NodeVisitor):
543544
544545
"""
545546

547+
def __init__(self, module_path, config):
548+
super(AssertionRewriter, self).__init__()
549+
self.module_path = module_path
550+
self.config = config
551+
546552
def run(self, mod):
547553
"""Find all assert statements in *mod* and rewrite them."""
548554
if not mod.body:
@@ -683,6 +689,10 @@ def visit_Assert(self, assert_):
683689
the expression is false.
684690
685691
"""
692+
if isinstance(assert_.test, ast.Tuple) and self.config is not None:
693+
fslocation = (self.module_path, assert_.lineno)
694+
self.config.warn('R1', 'assertion is always true, perhaps '
695+
'remove parentheses?', fslocation=fslocation)
686696
self.statements = []
687697
self.variables = []
688698
self.variable_counter = itertools.count()

_pytest/config.py

Lines changed: 31 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -64,8 +64,9 @@ class UsageError(Exception):
6464

6565
default_plugins = (
6666
"mark main terminal runner python pdb unittest capture skipping "
67-
"tmpdir monkeypatch recwarn pastebin helpconfig nose assertion genscript "
68-
"junitxml resultlog doctest cacheprovider setuponly setupplan").split()
67+
"tmpdir monkeypatch recwarn pastebin helpconfig nose assertion "
68+
"junitxml resultlog doctest cacheprovider freeze_support "
69+
"setuponly setupplan").split()
6970

7071
builtin_plugins = set(default_plugins)
7172
builtin_plugins.add("pytester")
@@ -686,6 +687,10 @@ def addoption(self, *optnames, **attrs):
686687
results in help showing '--two-words' only, but --twowords gets
687688
accepted **and** the automatic destination is in args.twowords
688689
"""
690+
conflict = set(optnames).intersection(
691+
name for opt in self.options for name in opt.names())
692+
if conflict:
693+
raise ValueError("option names %s already added" % conflict)
689694
option = Argument(*optnames, **attrs)
690695
self._addoption_instance(option, shortupper=False)
691696

@@ -999,14 +1004,16 @@ def _getini(self, name):
9991004
description, type, default = self._parser._inidict[name]
10001005
except KeyError:
10011006
raise ValueError("unknown configuration value: %r" %(name,))
1002-
try:
1003-
value = self.inicfg[name]
1004-
except KeyError:
1005-
if default is not None:
1006-
return default
1007-
if type is None:
1008-
return ''
1009-
return []
1007+
value = self._get_override_ini_value(name)
1008+
if value is None:
1009+
try:
1010+
value = self.inicfg[name]
1011+
except KeyError:
1012+
if default is not None:
1013+
return default
1014+
if type is None:
1015+
return ''
1016+
return []
10101017
if type == "pathlist":
10111018
dp = py.path.local(self.inicfg.config.path).dirpath()
10121019
l = []
@@ -1037,6 +1044,20 @@ def _getconftest_pathlist(self, name, path):
10371044
l.append(relroot)
10381045
return l
10391046

1047+
def _get_override_ini_value(self, name):
1048+
value = None
1049+
# override_ini is a list of list, to support both -o foo1=bar1 foo2=bar2 and
1050+
# and -o foo1=bar1 -o foo2=bar2 options
1051+
# always use the last item if multiple value set for same ini-name,
1052+
# e.g. -o foo=bar1 -o foo=bar2 will set foo to bar2
1053+
if self.getoption("override_ini", None):
1054+
for ini_config_list in self.option.override_ini:
1055+
for ini_config in ini_config_list:
1056+
(key, user_ini_value) = ini_config.split("=", 1)
1057+
if key == name:
1058+
value = user_ini_value
1059+
return value
1060+
10401061
def getoption(self, name, default=notset, skip=False):
10411062
""" return command line option value.
10421063

_pytest/freeze_support.py

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
"""
2+
Provides a function to report all internal modules for using freezing tools
3+
pytest
4+
"""
5+
6+
def pytest_namespace():
7+
return {'freeze_includes': freeze_includes}
8+
9+
10+
def freeze_includes():
11+
"""
12+
Returns a list of module names used by py.test that should be
13+
included by cx_freeze.
14+
"""
15+
import py
16+
import _pytest
17+
result = list(_iter_all_modules(py))
18+
result += list(_iter_all_modules(_pytest))
19+
return result
20+
21+
22+
def _iter_all_modules(package, prefix=''):
23+
"""
24+
Iterates over the names of all modules that can be found in the given
25+
package, recursively.
26+
Example:
27+
_iter_all_modules(_pytest) ->
28+
['_pytest.assertion.newinterpret',
29+
'_pytest.capture',
30+
'_pytest.core',
31+
...
32+
]
33+
"""
34+
import os
35+
import pkgutil
36+
if type(package) is not str:
37+
path, prefix = package.__path__[0], package.__name__ + '.'
38+
else:
39+
path = package
40+
for _, name, is_package in pkgutil.iter_modules([path]):
41+
if is_package:
42+
for m in _iter_all_modules(os.path.join(path, name), prefix=name + '.'):
43+
yield prefix + m
44+
else:
45+
yield prefix + name

0 commit comments

Comments
 (0)