[Python-modules-commits] [python-hypothesis] 01/05: Import python-hypothesis_1.17.0.orig.tar.gz

Tristan Seligmann mithrandi at moszumanska.debian.org
Wed Dec 16 15:18:23 UTC 2015


This is an automated email from the git hooks/post-receive script.

mithrandi pushed a commit to branch master
in repository python-hypothesis.

commit 917e33d40e98591ff160f4a41b17239b513c1f61
Author: Tristan Seligmann <mithrandi at debian.org>
Date:   Wed Dec 16 17:11:07 2015 +0200

    Import python-hypothesis_1.17.0.orig.tar.gz
---
 PKG-INFO                                  |   3 +-
 README.rst                                |   1 +
 setup.cfg                                 |   2 +-
 src/hypothesis.egg-info/PKG-INFO          |   3 +-
 src/hypothesis.egg-info/SOURCES.txt       |   1 -
 src/hypothesis.egg-info/requires.txt      |   6 +-
 src/hypothesis/core.py                    | 166 ++++++++++++++++++++++++++++--
 src/hypothesis/errors.py                  |  14 +++
 src/hypothesis/extra/fakefactory.py       |  10 +-
 src/hypothesis/internal/compat.py         |  20 ++--
 src/hypothesis/internal/compat3.py        |  23 -----
 src/hypothesis/searchstrategy/deferred.py |  11 +-
 src/hypothesis/settings.py                |  27 +++--
 src/hypothesis/version.py                 |   2 +-
 14 files changed, 227 insertions(+), 62 deletions(-)

diff --git a/PKG-INFO b/PKG-INFO
index 1db1069..c89d9a7 100644
--- a/PKG-INFO
+++ b/PKG-INFO
@@ -1,6 +1,6 @@
 Metadata-Version: 1.1
 Name: hypothesis
-Version: 1.16.0
+Version: 1.17.0
 Summary: A library for property based testing
 Home-page: https://github.com/DRMacIver/hypothesis
 Author: David R. MacIver
@@ -42,6 +42,7 @@ Description: ==========
         If you want to hear from people who are already using Hypothesis, some of them `have written
         about it <https://hypothesis.readthedocs.org/en/latest/endorsements.html>`_.
         
+        If you want to create a downstream package of Hypothesis, please read `these guidelines for packagers <http://hypothesis.readthedocs.org/en/latest/packaging.html>`_
         
         -------------------
         Ongoing Development
diff --git a/README.rst b/README.rst
index 7293f9c..ab6bb37 100644
--- a/README.rst
+++ b/README.rst
@@ -34,6 +34,7 @@ If you're looking for inspiration for writing your own QuickCheck clone,
 If you want to hear from people who are already using Hypothesis, some of them `have written
 about it <https://hypothesis.readthedocs.org/en/latest/endorsements.html>`_.
 
+If you want to create a downstream package of Hypothesis, please read `these guidelines for packagers <http://hypothesis.readthedocs.org/en/latest/packaging.html>`_
 
 -------------------
 Ongoing Development
diff --git a/setup.cfg b/setup.cfg
index a669c45..ebbec92 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -1,5 +1,5 @@
 [egg_info]
-tag_svn_revision = 0
 tag_build = 
+tag_svn_revision = 0
 tag_date = 0
 
diff --git a/src/hypothesis.egg-info/PKG-INFO b/src/hypothesis.egg-info/PKG-INFO
index 1db1069..c89d9a7 100644
--- a/src/hypothesis.egg-info/PKG-INFO
+++ b/src/hypothesis.egg-info/PKG-INFO
@@ -1,6 +1,6 @@
 Metadata-Version: 1.1
 Name: hypothesis
-Version: 1.16.0
+Version: 1.17.0
 Summary: A library for property based testing
 Home-page: https://github.com/DRMacIver/hypothesis
 Author: David R. MacIver
@@ -42,6 +42,7 @@ Description: ==========
         If you want to hear from people who are already using Hypothesis, some of them `have written
         about it <https://hypothesis.readthedocs.org/en/latest/endorsements.html>`_.
         
+        If you want to create a downstream package of Hypothesis, please read `these guidelines for packagers <http://hypothesis.readthedocs.org/en/latest/packaging.html>`_
         
         -------------------
         Ongoing Development
diff --git a/src/hypothesis.egg-info/SOURCES.txt b/src/hypothesis.egg-info/SOURCES.txt
index 482bff0..bcbc5a5 100644
--- a/src/hypothesis.egg-info/SOURCES.txt
+++ b/src/hypothesis.egg-info/SOURCES.txt
@@ -38,7 +38,6 @@ src/hypothesis/internal/charstree.py
 src/hypothesis/internal/chooser.py
 src/hypothesis/internal/classmap.py
 src/hypothesis/internal/compat.py
-src/hypothesis/internal/compat3.py
 src/hypothesis/internal/debug.py
 src/hypothesis/internal/distributions.py
 src/hypothesis/internal/examplesource.py
diff --git a/src/hypothesis.egg-info/requires.txt b/src/hypothesis.egg-info/requires.txt
index f85733e..285a5dc 100644
--- a/src/hypothesis.egg-info/requires.txt
+++ b/src/hypothesis.egg-info/requires.txt
@@ -5,12 +5,12 @@ ordereddict
 Counter
 
 [all]
-pytz
-django>=1.7
+fake-factory>=0.5.2,<=0.5.3
 pytest>=2.7.0
 pytz
 numpy>=1.9.0
-fake-factory>=0.5.2,<=0.5.3
+pytz
+django>=1.7
 
 [datetime]
 pytz
diff --git a/src/hypothesis/core.py b/src/hypothesis/core.py
index 2d6637f..09bd773 100644
--- a/src/hypothesis/core.py
+++ b/src/hypothesis/core.py
@@ -23,21 +23,24 @@ import math
 import time
 import inspect
 import binascii
+import warnings
 import functools
 import traceback
+from random import getstate as getglobalrandomstate
 from random import Random
 from itertools import islice
 from collections import namedtuple
 
 from hypothesis.errors import Flaky, Timeout, NoSuchExample, \
-    Unsatisfiable, BadTemplateDraw, InvalidArgument, \
-    UnsatisfiedAssumption, DefinitelyNoSuchExample
+    Unsatisfiable, BadTemplateDraw, InvalidArgument, FailedHealthCheck, \
+    UnsatisfiedAssumption, DefinitelyNoSuchExample, \
+    HypothesisDeprecationWarning
 from hypothesis.control import BuildContext
 from hypothesis.settings import Settings, Verbosity, note_deprecation
-from hypothesis.executors import executor
+from hypothesis.executors import executor, default_executor
 from hypothesis.reporting import report, debug_report, verbose_report, \
     current_verbosity
-from hypothesis.internal.compat import qualname, getargspec, \
+from hypothesis.internal.compat import hrange, qualname, getargspec, \
     unicode_safe_repr
 from hypothesis.internal.tracker import Tracker
 from hypothesis.internal.reflection import arg_string, impersonate, \
@@ -194,6 +197,10 @@ def simplify_template_such_that(
     assert isinstance(random, Random)
 
     yield t
+
+    if settings.max_shrinks <= 0 or not f(t):
+        return
+
     successful_shrinks = 0
 
     changed = True
@@ -259,7 +266,7 @@ def simplify_template_such_that(
 
 def best_satisfying_template(
     search_strategy, random, condition, settings, storage, tracker=None,
-    max_parameter_tries=None,
+    max_parameter_tries=None, start_time=None,
 ):
     """Find and then minimize a satisfying template.
 
@@ -270,7 +277,8 @@ def best_satisfying_template(
     """
     if tracker is None:
         tracker = Tracker()
-    start_time = time.time()
+    if start_time is None:
+        start_time = time.time()
 
     successful_shrinks = -1
     with settings:
@@ -461,6 +469,10 @@ def given(*generator_arguments, **generator_kwargs):
         for k in extra_kwargs:
             unused_kwargs[k] = HypothesisProvided(generator_kwargs[k])
 
+        hypothesis_owned_arguments = [
+            argspec.args[-1 - i] for i in hrange(len(argspec.defaults))
+        ] + list(unused_kwargs)
+
         @impersonate(test)
         @copy_argspec(
             test.__name__, argspec
@@ -472,6 +484,21 @@ def given(*generator_arguments, **generator_kwargs):
             selfy = None
             arguments, kwargs = convert_positional_arguments(
                 wrapped_test, arguments, kwargs)
+
+            for arg in hypothesis_owned_arguments:
+                try:
+                    value = kwargs[arg]
+                except KeyError:
+                    continue
+                if not isinstance(value, HypothesisProvided):
+                    note_deprecation(
+                        'Passing in explicit values to override Hypothesis '
+                        'provided values is deprecated and will no longer '
+                        'work in Hypothesis 2.0. If you need to do this, '
+                        'extract a common function and call that from a '
+                        'Hypothesis based test.', settings
+                    )
+
             # Anything in unused_kwargs hasn't been injected through
             # argspec.defaults, so we need to add them.
             for k in unused_kwargs:
@@ -537,6 +564,16 @@ def given(*generator_arguments, **generator_kwargs):
                     (k, convert_to_specifier(v)) for (k, v) in kwargs.items()))
             )
 
+            def fail_health_check(message):
+                message += (
+                    '\nSee http://hypothesis.readthedocs.org/en/latest/health'
+                    'checks.html for more information about this.'
+                )
+                if settings.strict:
+                    raise FailedHealthCheck(message)
+                else:
+                    warnings.warn(FailedHealthCheck(message))
+
             search_strategy = strategy(given_specifier, settings)
             search_strategy.validate()
 
@@ -546,17 +583,116 @@ def given(*generator_arguments, **generator_kwargs):
             else:
                 storage = None
 
+            start = time.time()
+            warned_random = [False]
+            perform_health_check = settings.perform_health_check
+            if Settings.default is not None:
+                perform_health_check &= Settings.default.perform_health_check
+
+            if perform_health_check:
+                initial_state = getglobalrandomstate()
+                with Settings(settings, verbosity=Verbosity.quiet):
+                    count = 0
+                    bad_draws = 0
+                    filtered_draws = 0
+                    while (
+                        count < 10 and time.time() < start + 1 and
+                        filtered_draws < 50 and bad_draws < 50
+                    ):
+                        try:
+                            test_runner(reify_and_execute(
+                                search_strategy,
+                                search_strategy.draw_template(
+                                    random,
+                                    search_strategy.draw_parameter(random)),
+                                lambda *args, **kwargs: None,
+                            ))
+                            count += 1
+                        except BadTemplateDraw:
+                            bad_draws += 1
+                        except UnsatisfiedAssumption:
+                            filtered_draws += 1
+                        except Exception:
+                            traceback.print_exc()
+                            if test_runner is default_executor:
+                                fail_health_check(
+                                    'An exception occurred during data '
+                                    'generation in initial health check. '
+                                    'This indicates a bug in the strategy. '
+                                    'This could either be a Hypothesis bug or '
+                                    "an error in a function you've passed to "
+                                    'it to construct your data.'
+                                )
+                            else:
+                                fail_health_check(
+                                    'An exception occurred during data '
+                                    'generation in initial health check. '
+                                    'This indicates a bug in the strategy. '
+                                    'This could either be a Hypothesis bug or '
+                                    'an error in a function you\'ve passed to '
+                                    'it to construct your data. Additionally, '
+                                    'you have a custom executor, which means '
+                                    'that this could be your executor failing '
+                                    'to handle a function which returns None. '
+                                )
+                if filtered_draws >= 50:
+                    fail_health_check((
+                        'It looks like your strategy is filtering out a lot '
+                        'of data. Health check found %d filtered examples but '
+                        'only %d good ones. This will make your tests much '
+                        'slower, and also will probably distort the data '
+                        'generation quite a lot. You should adapt your '
+                        'strategy to filter less.') % (
+                        filtered_draws, count
+                    ))
+                if bad_draws >= 50:
+                    fail_health_check(
+                        'Hypothesis is struggling to generate examples. '
+                        'This is often a sign of a recursive strategy which '
+                        'fans out too broadly. If you\'re using recursive, '
+                        'try to reduce the size of the recursive step or '
+                        'increase the maximum permitted number of leaves.'
+                    )
+                runtime = time.time() - start
+                if runtime > 1.0 or count < 10:
+                    fail_health_check((
+                        'Data generation is extremely slow: Only produced '
+                        '%d valid examples in %.2f seconds. Try decreasing '
+                        "size of the data you're generating (with e.g."
+                        'average_size or max_leaves parameters).'
+                    ) % (count, runtime))
+                if getglobalrandomstate() != initial_state:
+                    warned_random[0] = True
+                    fail_health_check(
+                        'Data generation depends on global random module. '
+                        'This makes results impossible to replay, which '
+                        'prevents Hypothesis from working correctly. '
+                        'If you want to use methods from random, use '
+                        'randoms() from hypothesis.strategies to get an '
+                        'instance of Random you can use.'
+                    )
+
             last_exception = [None]
             repr_for_last_exception = [None]
 
             def is_template_example(xs):
+                if perform_health_check and not warned_random[0]:
+                    initial_state = getglobalrandomstate()
                 record_repr = [None]
                 try:
-                    test_runner(reify_and_execute(
+                    result = test_runner(reify_and_execute(
                         search_strategy, xs, test,
                         record_repr=record_repr,
                     ))
+                    if result is not None:
+                        note_deprecation((
+                            'Tests run under @given should return None, but '
+                            '%s returned %r instead.'
+                            'In Hypothesis 2.0 this will become an error.'
+                        ) % (test.__name__, result), settings)
                     return False
+                except HypothesisDeprecationWarning:
+                    raise
                 except UnsatisfiedAssumption as e:
                     raise e
                 except Exception as e:
@@ -564,7 +700,19 @@ def given(*generator_arguments, **generator_kwargs):
                     repr_for_last_exception[0] = record_repr[0]
                     verbose_report(last_exception[0])
                     return True
-
+                finally:
+                    if (
+                        not warned_random[0] and
+                        perform_health_check and
+                        getglobalrandomstate() != initial_state
+                    ):
+                        warned_random[0] = True
+                        fail_health_check(
+                            'Your test used the global random module. '
+                            'This is unlikely to work correctly. You should '
+                            'consider using the randoms() strategy from '
+                            'hypothesis.strategies instead.'
+                        )
             is_template_example.__name__ = test.__name__
             is_template_example.__qualname__ = qualname(test)
 
@@ -572,7 +720,7 @@ def given(*generator_arguments, **generator_kwargs):
             try:
                 falsifying_template = best_satisfying_template(
                     search_strategy, random, is_template_example,
-                    settings, storage
+                    settings, storage, start_time=start,
                 )
             except NoSuchExample:
                 return
diff --git a/src/hypothesis/errors.py b/src/hypothesis/errors.py
index 4780852..d2b4e64 100644
--- a/src/hypothesis/errors.py
+++ b/src/hypothesis/errors.py
@@ -16,6 +16,8 @@
 
 from __future__ import division, print_function, absolute_import
 
+import warnings
+
 
 class HypothesisException(Exception):
 
@@ -162,3 +164,15 @@ class AbnormalExit(HypothesisException):
 
     """Raised when a test running in a child process exits without returning or
     raising an exception."""
+
+
+class FailedHealthCheck(HypothesisException, Warning):
+    """Raised when a test fails a preliminary healthcheck that occurs before
+    execution."""
+
+
+class HypothesisDeprecationWarning(HypothesisException, DeprecationWarning):
+    pass
+
+
+warnings.simplefilter(u'once', HypothesisDeprecationWarning)
diff --git a/src/hypothesis/extra/fakefactory.py b/src/hypothesis/extra/fakefactory.py
index d557c50..618548c 100644
--- a/src/hypothesis/extra/fakefactory.py
+++ b/src/hypothesis/extra/fakefactory.py
@@ -16,6 +16,7 @@
 
 from __future__ import division, print_function, absolute_import
 
+import random as globalrandom
 from random import Random
 
 import faker
@@ -94,8 +95,13 @@ class FakeFactoryStrategy(SearchStrategy):
 
     def gen_example(self, random, locales):
         factory = self.factory_for(random.choice(locales))
-        factory.seed(random.getrandbits(128))
-        return text_type(getattr(factory, self.source)())
+        original = globalrandom.getstate()
+        seed = random.getrandbits(128)
+        try:
+            factory.seed(seed)
+            return text_type(getattr(factory, self.source)())
+        finally:
+            globalrandom.setstate(original)
 
     def basic_simplify(self, random, template):
         for _ in hrange(10):
diff --git a/src/hypothesis/internal/compat.py b/src/hypothesis/internal/compat.py
index 36064dc..115dc6c 100644
--- a/src/hypothesis/internal/compat.py
+++ b/src/hypothesis/internal/compat.py
@@ -89,9 +89,10 @@ if PY3:
     def escape_unicode_characters(s):
         return codecs.encode(s, 'unicode_escape').decode('ascii')
 
-    def quiet_raise(exc):
-        from hypothesis.internal.compat3 import quiet_raise as q
-        q(exc)
+    exec("""
+def quiet_raise(exc):
+    raise exc from None
+""")
 else:
     VALID_PYTHON_IDENTIFIER = re.compile(
         r"^[a-zA-Z_][a-zA-Z0-9_]*$"
@@ -102,10 +103,17 @@ else:
 
     def unicode_safe_repr(x):
         try:
-            r = type(x).__repr__(x)
-        except TypeError:
-            # Workaround for https://bitbucket.org/pypy/pypy/issues/2083/
             r = repr(x)
+        except UnicodeEncodeError:
+            r = type(x).__repr__(x)
+            from hypothesis.settings import note_deprecation
+            note_deprecation((
+                'Type %s has a broken repr implementation. Calling __repr__ '
+                'on it returned %r, which cannot be represented as ASCII '
+                'text. This is not permitted in Python 2. Hypothesis is '
+                'currently working around this, but will stop doing so in '
+                'Hypothesis 2.0. You should fix your code.'
+            ) % (type(x).__name__, r))
         if isinstance(r, unicode):
             return r
         else:
diff --git a/src/hypothesis/internal/compat3.py b/src/hypothesis/internal/compat3.py
deleted file mode 100644
index e301277..0000000
--- a/src/hypothesis/internal/compat3.py
+++ /dev/null
@@ -1,23 +0,0 @@
-# coding=utf-8
-#
-# This file is part of Hypothesis (https://github.com/DRMacIver/hypothesis)
-#
-# Most of this work is copyright (C) 2013-2015 David R. MacIver
-# (david at drmaciver.com), but it contains contributions by others. See
-# https://github.com/DRMacIver/hypothesis/blob/master/CONTRIBUTING.rst for a
-# full list of people who may hold copyright, and consult the git log if you
-# need to determine who owns an individual contribution.
-#
-# This Source Code Form is subject to the terms of the Mozilla Public License,
-# v. 2.0. If a copy of the MPL was not distributed with this file, You can
-# obtain one at http://mozilla.org/MPL/2.0/.
-#
-# END HEADER
-
-# pylint: skip-file
-
-from __future__ import division, print_function, absolute_import
-
-
-def quiet_raise(exc):
-    raise exc from None
diff --git a/src/hypothesis/searchstrategy/deferred.py b/src/hypothesis/searchstrategy/deferred.py
index 9bdb83f..ef4f5d1 100644
--- a/src/hypothesis/searchstrategy/deferred.py
+++ b/src/hypothesis/searchstrategy/deferred.py
@@ -16,6 +16,7 @@
 
 from __future__ import division, print_function, absolute_import
 
+from hypothesis import Settings
 from hypothesis.internal.compat import hrange, getargspec, \
     unicode_safe_repr
 from hypothesis.internal.reflection import arg_string, \
@@ -62,14 +63,16 @@ class DeferredStrategy(SearchStrategy):
         self.__kwargs = dict(
             (k, tupleize(v)) for k, v in kwargs.items()
         )
+        self.__settings = Settings.default or Settings()
 
     @property
     def wrapped_strategy(self):
         if self.__wrapped_strategy is None:
-            self.__wrapped_strategy = self.__function(
-                *self.__args,
-                **self.__kwargs
-            )
+            with self.__settings:
+                self.__wrapped_strategy = self.__function(
+                    *self.__args,
+                    **self.__kwargs
+                )
         return self.__wrapped_strategy
 
     def validate(self):
diff --git a/src/hypothesis/settings.py b/src/hypothesis/settings.py
index 7789ccc..6e7b720 100644
--- a/src/hypothesis/settings.py
+++ b/src/hypothesis/settings.py
@@ -29,7 +29,7 @@ import warnings
 import threading
 from collections import namedtuple
 
-from hypothesis.errors import InvalidArgument
+from hypothesis.errors import InvalidArgument, HypothesisDeprecationWarning
 from hypothesis.utils.conventions import not_set
 from hypothesis.utils.dynamicvariables import DynamicVariable
 
@@ -415,7 +415,12 @@ Settings.define_setting(
     default=os.getenv(u'HYPOTHESIS_STRICT_MODE') == u'true',
     description="""
 If set to True, anything that would cause Hypothesis to issue a warning will
-instead raise an error.
+instead raise an error. Note that new warnings may be added at any time, so
+running with strict set to True means that new Hypothesis releases may validly
+break your code.
+
+You can enable this setting temporarily by setting the HYPOTHESIS_STRICT_MODE
+environment variable to the string 'true'.
 """
 )
 
@@ -509,20 +514,22 @@ Settings.define_setting(
     description=u'Average length of lists to use'
 )
 
+Settings.define_setting(
+    u'perform_health_check',
+    default=True,
+    description=u"""
+If set to True, Hypothesis will run a preliminary health check before
+attempting to actually execute your test.
+"""
+)
+
 Settings.lock_further_definitions()
 
 Settings.register_profile('default', Settings())
 Settings.load_profile('default')
 
 
-class HypothesisDeprecationWarning(DeprecationWarning):
-    pass
-
-
-warnings.simplefilter(u'once', HypothesisDeprecationWarning)
-
-
-def note_deprecation(message, settings):
+def note_deprecation(message, settings=None):
     # If *either* self or the current default are non-strict
     # then this should be an error. This is to handle e.g. the case
     # where defining a new setting while non-strict updates a
diff --git a/src/hypothesis/version.py b/src/hypothesis/version.py
index f4a1011..b74ae75 100644
--- a/src/hypothesis/version.py
+++ b/src/hypothesis/version.py
@@ -16,5 +16,5 @@
 
 from __future__ import division, print_function, absolute_import
 
-__version_info__ = (1, 16, 0)
+__version_info__ = (1, 17, 0)
 __version__ = u'.'.join(map(str, __version_info__))

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/python-modules/packages/python-hypothesis.git



More information about the Python-modules-commits mailing list