NewYour coding agent can read the release notes before it upgrades.Set up the MCP server →
PyPI · #407 most downloaded on PyPI
The property-based testing library for Python
Last release 7 days ago
28 Sep 2026
Ships on a steady schedule
a new release about every 9 days
Nearly every release is documented
notes for 60 of the last 60 stable releases
Nothing withdrawn
no release was ever pulled
14 years old
1571 releases · first in 2013
This patch fixes quadratic-time behaviour when summarising the statistics of a test run, which Hypothesis does for every test when running under pytes
This patch fixes quadratic-time behaviour when summarising the
statistics of a test run, which Hypothesis does for every test when
running under pytest. This avoids an apparent hang after the last test
case with a high number of test cases (>100k).
The canonical version of these notes (with links) is on readthedocs.
This patch makes writes to the cache of constants collected from local source files atomic. Previously, a concurrent process sharing the same ".hypoth
This patch makes writes to the cache of constants collected from local
source files atomic. Previously, a concurrent process sharing the same
".hypothesis" directory, such as another pytest-xdist worker, could
read a partially written cache file, which silently changed the data
generated for a given "@seed" (issue #4885).
The canonical version of these notes (with links) is on readthedocs.
One column per quarter.
We now publish abi3 wheels for Linux s390x (manylinux) and Linux i686 (musllinux).
We now publish abi3 wheels for Linux s390x (manylinux) and Linux i686
(musllinux).
The canonical version of these notes (with links) is on readthedocs.
We now publish abi3 wheels for Linux s390x (manylinux) and Linux i686 (musllinux).
"datetimes()" now generates "tricky" datetimes more often: values on or near daylight-saving and other utc-offset transitions of the drawn timezone -
"datetimes()" now generates "tricky" datetimes more often: values on
or near daylight-saving and other utc-offset transitions of the drawn
timezone - including imaginary wall times, and ambiguous ones with
each value of "fold" - as well as times adjacent to leap seconds and
to well-known datetimes like the millennium and the end of the signed
32-bit Unix epoch (issue #69).
This release also fixes some rare internal errors, where an error
raised partway through updating an internal cache - for example by a
deeply recursive strategy raising "RecursionError" - could leave that
cache corrupted.
The canonical version of these notes (with links) is on readthedocs.
This patch improves shrinking and generation for collection strategies which reject some drawn elements, such as "lists()" with "unique=True". Rejecte
This patch improves shrinking and generation for collection strategies
which reject some drawn elements, such as "lists()" with
"unique=True". Rejected elements are now marked as discarded, so the
shrinker can delete them wholesale and generation avoids revisiting
choices that would be rejected again.
The canonical version of these notes (with links) is on readthedocs.
This patch improves shrinking and generation for collection strategies which reject some drawn elements, such as ~hypothesis.strategies.lists with unique=True. Rejected elements are now marked as discarded, so the shrinker can delete them wholesale and generation avoids revisiting choices that would be rejected again.
Test case observations from observability now give more detail about why a test case failed or was abandoned (issue #3845 ). "metadata" includes a new
Test case observations from observability now give more detail about
why a test case failed or was abandoned (issue #3845). "metadata"
includes a new "status_reason_location" key: a "filename:lineno"
location for the "status_reason", if known - for example the location
of a failing "assume()" call, the ".filter()" call whose predicate
rejected the last drawn value, or the exception for failing tests.
Test cases which exceeded the maximum allowed size now also report a
nonempty "status_reason".
The canonical version of these notes (with links) is on readthedocs.
The "Phase.explain" phase now also varies interactive draws from "data()", annotating each freely-variable "Draw n: ..." line with an "# or any other
The "Phase.explain" phase now also varies interactive draws from
"data()", annotating each freely-variable "Draw n: ..." line with an
"# or any other generated value" comment, just like "@given" arguments
(issue #4403).
This release also fixes two explain-phase bugs: failing test cases
found just as the set of possible inputs was fully enumerated were
reported without running the "Phase.shrink" and "Phase.explain"
phases, and the explain phase could fail to report that the commented
parts can be varied together if the failing example ended with an
uncommented part.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes the "redistribute_numeric_pairs" shrink pass, which incorrectly checked "node1.type" instead of "node2.type" when guarding against fl
This patch fixes the "redistribute_numeric_pairs" shrink pass, which
incorrectly checked "node1.type" instead of "node2.type" when guarding
against float precision loss above "MAX_PRECISE_INTEGER".
The canonical version of these notes (with links) is on readthedocs.
This patch fixes the redistribute_numeric_pairs shrink pass, which incorrectly checked node1.type instead of node2.type when guarding against float precision loss above MAX_PRECISE_INTEGER.
This patch fixes several "from_regex()" bugs (issue #4857, issue
This patch fixes several "from_regex()" bugs (issue #4857, issue #4858, and issue #4859):
Character classes which combine a negative category with other members, like "[\W_]", now match the union of their members instead of incorrectly excluding characters.
Patterns compiled with the "re.ASCII" flag are now handled correctly: inverted categories such as "\D" match the complement of their ascii counterpart, including non-ascii characters; explicit characters and ranges in character classes are not restricted to ascii; and only ascii characters casefold under "re.IGNORECASE".
Subpatterns which cannot be generated from the "alphabet", but may be repeated zero times - like "b*" in "st.from_regex(r"ab", alphabet="a")" - no longer raise an error.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes several ~hypothesis.strategies.from_regex bugs (4857, 4858, and 4859):
Character classes which combine a negative category with other members, like [\W_], now match the union of their members instead of incorrectly excluding characters.
Patterns compiled with the python:re.ASCII flag are now handled correctly: inverted categories such as \D match the complement of their ascii counterpart, including non-ascii characters; explicit characters and ranges in character classes are not restricted to ascii; and only ascii characters casefold under python:re.IGNORECASE.
Subpatterns which cannot be generated from the alphabet, but may be repeated zero times - like b* in st.from_regex(r"a*b*", alphabet="a") - no longer raise an error.
This patch improves the performance of "one_of()" when it can be simplified to a single real strategy, for example "st.integers() | st.nothing()".
This patch improves the performance of "one_of()" when it can be
simplified to a single real strategy, for example "st.integers() |
st.nothing()".
The canonical version of these notes (with links) is on readthedocs.
This patch improves the performance of |st.one_of| when it can be simplified to a single real strategy, for example st.integers() | st.nothing().
This patch provides a better error message for some "from_regex()" cases where the passed pattern and alphabet were incompatible, as in "st.from_regex
This patch provides a better error message for some "from_regex()"
cases where the passed pattern and alphabet were incompatible, as in
"st.from_regex(r"\d", alphabet="abc")".
Thanks to Dmitry Dygalo for this fix!
The canonical version of these notes (with links) is on readthedocs.
This patch provides a better error message for some ~hypothesis.strategies.from_regex cases where the passed pattern and alphabet were incompatible, as in st.from_regex(r"\d", alphabet="abc").
Thanks to Dmitry Dygalo for this fix!
This release adds support for Python 3.15. "from_type()" can now resolve the new "sentinel" builtin.
This release adds support for Python 3.15. "from_type()" can now
resolve the new "sentinel" builtin.
The canonical version of these notes (with links) is on readthedocs.
This release adds support for Python 3.15. |st.from_type| can now resolve the new sentinel builtin.
We now publish abi3 wheels for Windows arm64 and Linux ppc64le (manylinux + musllinux; issue #4852 ).
We now publish abi3 wheels for Windows arm64 and Linux ppc64le
(manylinux + musllinux; issue #4852).
The canonical version of these notes (with links) is on readthedocs.
We now publish abi3 wheels for Windows arm64 and Linux ppc64le (manylinux + musllinux; 4852).
This release continues the terminology change in version 6.159.0, updating more internal wording and names from "example" to "test case".
This release continues the terminology change in version 6.159.0,
updating more internal wording and names from "example" to "test
case".
The canonical version of these notes (with links) is on readthedocs.
This release continues the terminology change in version 6.159.0, updating more internal wording and names from "example" to "test case".
This release improves our heuristic for when to run the "Phase.target" phase, which optimises scores from "hypothesis.target()". Behaviour is unchange
This release improves our heuristic for when to run the "Phase.target"
phase, which optimises scores from "hypothesis.target()". Behaviour is
unchanged for "max_examples" below 1000. For larger budgets we now
start optimising much earlier, and alternate between generation and
optimisation for as long as scores keep improving, instead of running
a single optimisation pass halfway through the run. Exploratory
searches using "target()" with a large budget should now make much
better use of it (issue #3176).
The canonical version of these notes (with links) is on readthedocs.
This release improves our heuristic for when to run the |Phase.target| phase, which optimises scores from hypothesis.target. Behaviour is unchanged for ~hypothesis.settings.max_examples below 1000. For larger budgets we now start optimising much earlier, and alternate between generation and optimisation for as long as scores keep improving, instead of running a single optimisation pass halfway through the run. Exploratory searches using ~hypothesis.target with a large budget should now make much better use of it (3176).
This patch fixes "BytestringProvider.draw_float" so that it can generate negative floats. Previously, only 64 bits were drawn for a 65-bit float index
This patch fixes "BytestringProvider.draw_float" so that it can
generate negative floats. Previously, only 64 bits were drawn for a
65-bit float index format, so the sign bit was always zero and
negative floats could never be produced.
The canonical version of these notes (with links) is on readthedocs.
This release extends a recent shrinking improvement to many more strategies. In unions like "wide_strategy | specific_strategy", values produced by th
This release extends a recent shrinking improvement to many more strategies. In unions like "wide_strategy | specific_strategy", values produced by the specific branch can now be re-encoded and shrunk as if generated by the wider branch when the strategies involved include "sampled_from()", "lists()", "tuples()", "dictionaries()" and "fixed_dictionaries()", "builds()" of a dataclass, "permutations()", the "dates()" family of strategies, and filtered, deferred, or recursive combinations of them.
The canonical version of these notes (with links) is on readthedocs.
This release extends a recent shrinking improvement to many more strategies. In unions like wide_strategy | specific_strategy, values produced by the specific branch can now be re-encoded and shrunk as if generated by the wider branch when the strategies involved include ~hypothesis.strategies.sampled_from, ~hypothesis.strategies.lists, ~hypothesis.strategies.tuples, ~hypothesis.strategies.dictionaries and ~hypothesis.strategies.fixed_dictionaries, ~hypothesis.strategies.builds of a dataclass, ~hypothesis.strategies.permutations, the ~hypothesis.strategies.dates family of strategies, and filtered, deferred, or recursive combinations of them.
This release improves shrinking for strategies like st.text() | some_more_complicated_strategy: values produced by the more specific strategy can now
This release improves shrinking for strategies like st.text() | some_more_complicated_strategy: values produced by the more specific strategy can now be shrunk as if they had been generated by the wider strategy. (Values from ~hypothesis.strategies.just are the exception, as generating them makes no choices which could be re-encoded.)
"characters()" now issues the new "NonRoundTrippableCharactersWarning" if the "codec" argument allows generating characters which encode successfully
"characters()" now issues the new "NonRoundTrippableCharactersWarning" if the "codec" argument allows generating characters which encode successfully but do not decode back to the same character - for example the yen sign becomes a backslash under "shift_jis" - since strings containing them do not round-trip (issue #4813). Pass each such character in "include_characters" to generate it without the warning, or in "exclude_characters" to generate only characters which round-trip.
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.strategies.characters now issues the new ~hypothesis.errors.NonRoundTrippableCharactersWarning if the codec argument allows generating characters which encode successfully but do not decode back to the same character - for example the yen sign becomes a backslash under shift_jis - since strings containing them do not round-trip (4813). Pass each such character in include_characters to generate it without the warning, or in exclude_characters to generate only characters which round-trip.
"functions()" now generates functions of the same kind as the "like=" argument, so that async functions, generator functions, and async generator func
"functions()" now generates functions of the same kind as the "like=" argument, so that async functions, generator functions, and async generator functions can be imitated as well as plain functions (issue #4149). "pure=True" is only supported for plain functions.
Generated generator functions yield a list of values drawn from "returns", inferring e.g. "returns=integers()" from an "Iterator[int]" or "AsyncIterator[int]" return-type annotation, and generated async functions follow Trio-style checkpoint semantics.
The canonical version of these notes (with links) is on readthedocs.
Now that we combine coverage data across our CI jobs (issue #4261), this patch removes around a hundred "# pragma: no cover" comments which are no lon
Now that we combine coverage data across our CI jobs (issue #4261), this patch removes around a hundred "# pragma: no cover" comments which are no longer needed, and expands our 100%-coverage requirement to several previously-omitted files.
The "explain" phase no longer reports lines inside the standard library, which were occasionally included in (and made for misleading) explanations.
The constants-collection feature introduced in version 6.131.1 now also collects the float components of complex literals like "3.5j".
The canonical version of these notes (with links) is on readthedocs.
The "alphabet=" argument of "from_regex()" now accepts any collection of length-one strings, such as a tuple or list of characters (issue
The "alphabet=" argument of "from_regex()" now accepts any collection of length-one strings, such as a tuple or list of characters (issue #4829). This matches the existing behavior of "text()".
The canonical version of these notes (with links) is on readthedocs.
The alphabet= argument of |st.from_regex| now accepts any collection of length-one strings, such as a tuple or list of characters (4829). This matches the existing behavior of |st.text|.
This release adds support for generating timezone-aware datetimes in hypothesis.extra.pandas. You can now pass a "DatetimeTZDtype" - such as ""datetim
This release adds support for generating timezone-aware datetimes in hypothesis.extra.pandas. You can now pass a "DatetimeTZDtype" - such as ""datetime64[ns, UTC]"" - as the "dtype" of a "series()", "indexes()", or "column()", and every value will share that single timezone. The datetime resolution is taken from the dtype, so you can also generate e.g. ""datetime64[us, UTC]"" columns, and for UTC and other fixed-offset timezones the generated values cover the full range representable at that resolution - which for coarser units is far wider than the "datetime64[ns]" bounds of roughly 1677-2262 (issue #4020).
Timezone-aware generation requires pandas >= 2.1. Generated values include "NaT" unless you pass an elements strategy which excludes it.
The canonical version of these notes (with links) is on readthedocs.
This release adds support for generating timezone-aware datetimes in hypothesis.extra.pandas. You can now pass a ~pandas.DatetimeTZDtype - such as "datetime64[ns, UTC]" - as the dtype of a ~hypothesis.extra.pandas.series, ~hypothesis.extra.pandas.indexes, or ~hypothesis.extra.pandas.column, and every value will share that single timezone. The datetime resolution is taken from the dtype, so you can also generate e.g. "datetime64[us, UTC]" columns, and for UTC and other fixed-offset timezones the generated values cover the full range representable at that resolution - which for coarser units is far wider than the datetime64[ns] bounds of roughly 1677-2262 (4020).
Timezone-aware generation requires pandas >= 2.1. Generated values include NaT unless you pass an elements strategy which excludes it.
This patch removes a redundant "# pragma: no cover" comment. There is no user-visible change.
This patch removes a redundant "# pragma: no cover" comment. There is no user-visible change.
The canonical version of these notes (with links) is on readthedocs.
This patch removes a redundant # pragma: no cover comment. There is no user-visible change.
This patch updates our vendored list of top-level domains, which is used by the provisional "domains()" strategy.
This patch updates our vendored list of top-level domains, which is used by the provisional "domains()" strategy.
The canonical version of these notes (with links) is on readthedocs.
This patch updates our vendored list of top-level domains, which is used by the provisional ~hypothesis.provisional.domains strategy.
This patch improves the display of functions generated by "functions()". If the "returns=" strategy can only produce a single value, the function is n
This patch improves the display of functions generated by "functions()". If the "returns=" strategy can only produce a single value, the function is now shown as a constant lambda such as "f=lambda x: 3", instead of noting each call to it separately.
We also respect the "repr_pretty()" method of objects which define one in a few more places, such as the arguments of a failing example.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes a bug where a lambda could be displayed with the definition of an unrelated lambda which happened to take the same arguments - for ex
This patch fixes a bug where a lambda could be displayed with the definition of an unrelated lambda which happened to take the same arguments - for example a function generated by "functions()" when shown in a failing example.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes a bug where a lambda could be displayed with the definition of an unrelated lambda which happened to take the same arguments - for example a function generated by ~hypothesis.strategies.functions when shown in a failing example.
We now publish abi3 wheels for Linux armv7l, for both manylinux and musllinux (issue #4818).
We now publish abi3 wheels for Linux armv7l, for both manylinux and musllinux (issue #4818).
The canonical version of these notes (with links) is on readthedocs.
We now publish abi3 wheels for Linux armv7l, for both manylinux and musllinux (4818).
This patch improves our internal "@proxies" decorator, which now preserves the kind of the decorated function: proxies for async functions, generator
This patch improves our internal "@proxies" decorator, which now preserves the kind of the decorated function: proxies for async functions, generator functions, and async generator functions are themselves functions of the same kind. This prepares for upcoming "functions()" support (issue #4149).
The canonical version of these notes (with links) is on readthedocs.
This patch improves our internal @proxies decorator, which now preserves the kind of the decorated function: proxies for async functions, generator functions, and async generator functions are themselves functions of the same kind. This prepares for upcoming ~hypothesis.strategies.functions support (4149).
We now publish abi3 wheels for Linux riscv64, for both manylinux and musllinux (issue #4815).
We now publish abi3 wheels for Linux riscv64, for both manylinux and musllinux (issue #4815).
The canonical version of these notes (with links) is on readthedocs.
We now publish abi3 wheels for Linux riscv64, for both manylinux and musllinux (4815).
"from_lark()" could generate strings which the grammar's lexer tokenizes differently than the terminal they were generated for, and which therefore fa
"from_lark()" could generate strings which the grammar's lexer tokenizes differently than the terminal they were generated for, and which therefore fail to parse - for example "'"""'" for Lark's built- in "ESCAPED_STRING" terminal (issue #4325). Terminal strategies now only generate strings which the lexer would match in their entirety.
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.extra.lark.from_lark could generate strings which the grammar's lexer tokenizes differently than the terminal they were generated for, and which therefore fail to parse - for example '"""' for Lark's built-in ESCAPED_STRING terminal (4325). Terminal strategies now only generate strings which the lexer would match in their entirety.
Values recorded with "note()" are now included in observability reports, as an ordered list of strings under the "metadata.notes" key of each test-cas
Values recorded with "note()" are now included in observability reports, as an ordered list of strings under the "metadata.notes" key of each test-case observation. Previously, notes were only shown in the terminal for the minimal failing test case (or for every test case under "Verbosity.verbose"), and never appeared in observations at all.
The canonical version of these notes (with links) is on readthedocs.
Values recorded with ~hypothesis.note are now included in observability reports, as an ordered list of strings under the metadata.notes key of each test-case observation. Previously, notes were only shown in the terminal for the |minimal failing test case| (or for every test case under |Verbosity.verbose|), and never appeared in observations at all.
"Bundle" now supports efficient ".filter()" and ".map()" methods, which compose with "consumes()" in either order (issue #3944). Previously, "consumes
"Bundle" now supports efficient ".filter()" and ".map()" methods, which compose with "consumes()" in either order (issue #3944). Previously, "consumes(bundle).filter(fn)" could remove rejected values from the bundle while retrying, and "consumes(bundle.filter(fn))" was a type error; filtered draws now select among currently-matching values and consume only the value which was actually drawn.
Thanks to Reagan Lee for the initial implementation of this feature in pull request #4084!
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.stateful.Bundle now supports efficient |.filter| and |.map| methods, which compose with ~hypothesis.stateful.consumes in either order (3944). Previously, consumes(bundle).filter(fn) could remove rejected values from the bundle while retrying, and consumes(bundle.filter(fn)) was a type error; filtered draws now select among currently-matching values and consume only the value which was actually drawn.
Thanks to Reagan Lee for the initial implementation of this feature in 4084!
This is not a breaking change, as we have intentionally not changed any code APIs. In particular, "settings.max_examples" has not been changed.
Hypothesis has historically referred to the single execution of a test function as an "example". However, we have in recent years tended to call a single execution a "test case" instead, which we think is a more precise and less overloaded term.
This release updates user-facing documentation, log messages, and error messages to use the "test case" terminology. Some observability fields which contain raw strings from Hypothesis might change in format as a result.
This is not a breaking change, as we have intentionally not changed any code APIs. In particular, "settings.max_examples" has not been changed.
The canonical version of these notes (with links) is on readthedocs.
This patch implements filter-rewriting for "times()" and "datetimes()": simple comparison filters such as ".filter(partial(operator.ge, bound))" are r
This patch implements filter-rewriting for "times()" and "datetimes()": simple comparison filters such as ".filter(partial(operator.ge, bound))" are rewritten into efficient bounds, as "dates()" already did. This includes strategies inferred from annotated-types bounds like "Annotated[datetime, Gt(...)]", and contradictory filters now give an empty strategy instead of failing health checks.
The canonical version of these notes (with links) is on readthedocs.
This patch implements filter-rewriting for ~hypothesis.strategies.times and ~hypothesis.strategies.datetimes: simple comparison filters such as .filter(partial(operator.ge, bound)) are rewritten into efficient bounds, as ~hypothesis.strategies.dates already did. This includes strategies inferred from annotated-types bounds like Annotated[datetime, Gt(...)], and contradictory filters now give an empty strategy instead of failing health checks.
"datetimes()" now accepts timezone-aware "min_value" and "max_value" bounds, which are treated as moments in time. In this case "timezones" defaults t
"datetimes()" now accepts timezone-aware "min_value" and "max_value" bounds, which are treated as moments in time. In this case "timezones" defaults to "timezones()", and each generated datetime lies between the two moments. Passing one aware and one naive bound is an error.
If annotated-types has been imported, the overloaded type hints for this strategy now distinguish naive from aware datetimes using "Timezone" metadata.
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.strategies.datetimes now accepts timezone-aware min_value and max_value bounds, which are treated as moments in time. In this case timezones defaults to ~hypothesis.strategies.timezones, and each generated datetime lies between the two moments. Passing one aware and one naive bound is an error.
If annotated-types has been imported, the overloaded type hints for this strategy now distinguish naive from aware datetimes using Timezone metadata.
This patch continues our migration of Hypothesis internals to rust (issue #4740), porting some internal float helpers. There should be no user-visible
This patch continues our migration of Hypothesis internals to rust (issue #4740), porting some internal float helpers. There should be no user-visible change. If you see any change in behavior, please open an issue.
The canonical version of these notes (with links) is on readthedocs.
Internal refactoring of how "Phase.explain" tracks which parts of a failing example can vary, with no user-visible change.
Internal refactoring of how "Phase.explain" tracks which parts of a failing example can vary, with no user-visible change.
The canonical version of these notes (with links) is on readthedocs.
Internal refactoring of how |Phase.explain| tracks which parts of a failing example can vary, with no user-visible change.
"from_type()" now supports the annotated-types "Timezone" constraint on "datetime" and "time", resolves the typing-extensions "TypeAliasType" backport
"from_type()" now supports the annotated-types "Timezone" constraint on "datetime" and "time", resolves the typing-extensions "TypeAliasType" backport as well as the native form from Python 3.12+, and suggests subscripting generic aliases like "annotated_types.LowerCase" if they are mistakenly passed as "Annotated" metadata.
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.strategies.from_type now supports the annotated-types Timezone constraint on ~python:datetime.datetime and ~python:datetime.time, resolves the typing-extensions TypeAliasType backport as well as the native form from Python 3.12+, and suggests subscripting generic aliases like annotated_types.LowerCase if they are mistakenly passed as Annotated metadata.
This release improves observability output under symbolic backends by displaying arguments generated by "data()" as "data(...)".
This release improves observability output under symbolic backends by displaying arguments generated by "data()" as "data(...)".
Thanks to zhangli091011 for this fix!
The canonical version of these notes (with links) is on readthedocs.
This release improves observability output under symbolic backends by displaying arguments generated by ~hypothesis.strategies.data as data(...).
Thanks to zhangli091011 for this fix!
This patch improves the performance of unique collections drawing from a fixed pool of elements, such as "sets()" of "sampled_from()", under symbolic-
This patch improves the performance of unique collections drawing from a fixed pool of elements, such as "sets()" of "sampled_from()", under symbolic-execution backends such as hypothesis-crosshair.
The canonical version of these notes (with links) is on readthedocs.
This patch improves the performance of unique collections drawing from a fixed pool of elements, such as ~hypothesis.strategies.sets of ~hypothesis.strategies.sampled_from, under symbolic-execution backends such as hypothesis-crosshair.
This patch fixes a bug where calling ".flatmap()" on a "consumes()" bundle raised an error (issue #4427).
This patch fixes a bug where calling ".flatmap()" on a "consumes()" bundle raised an error (issue #4427).
The canonical version of these notes (with links) is on readthedocs.
This patch fixes a bug where calling .flatmap() on a ~hypothesis.stateful.consumes bundle raised an error (4427).
This patch fixes "GitHubArtifactDatabase" failing to download artifacts due to a colliding "Authorization" header.
This patch fixes "GitHubArtifactDatabase" failing to download artifacts due to a colliding "Authorization" header.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes |GitHubArtifactDatabase| failing to download artifacts due to a colliding Authorization header.
We now publish abi3 wheels for 32-bit linux and 32-bit windows.
We now publish abi3 wheels for 32-bit linux and 32-bit windows.
The canonical version of these notes (with links) is on readthedocs.
In addition to our version-specific wheels, we now also publish "abi3" wheels, built against the 3.10 stable ABI.
In addition to our version-specific wheels, we now also publish "abi3" wheels, built against the 3.10 stable ABI.
The canonical version of these notes (with links) is on readthedocs.
In addition to our version-specific wheels, we now also publish abi3 wheels, built against the 3.10 stable ABI.
Fix not uploading source distributions to PyPI, as of v6.156.0.
Fix not uploading source distributions to PyPI, as of v6.156.0.
This patch fixes a KeyError in |GitHubArtifactDatabase| when reading an artifact whose zip file contains no explicit directory entries, which is the c
This patch fixes a KeyError in |GitHubArtifactDatabase| when reading an
artifact whose zip file contains no explicit directory entries, which is the
case for zips produced by actions/upload-artifact.
This patch fixes our build pipeline from v6.156.0, so that wheels are actually published.
This patch fixes our build pipeline from v6.156.0, so that wheels are actually published.
This patch fixes our build pipeline from 6.156.0, so that wheels are actually published.
This patch fixes a thread-safety bug where concurrent use of the same strategy instance could error in rare cases. (issue #4475).
This patch fixes a thread-safety bug where concurrent use of the same strategy instance could error in rare cases. (issue #4475).
The canonical version of these notes (with links) is on readthedocs.
This patch fixes a thread-safety bug where concurrent use of the same strategy instance could error in rare cases. (4475).
This patch replaces some internal "%"-style string formatting with f-strings. There is no user-visible change.
This patch replaces some internal "%"-style string formatting with f-strings. There is no user-visible change.
The canonical version of these notes (with links) is on readthedocs.
This patch replaces some internal %-style string formatting with f-strings. There is no user-visible change.
"dates()" now raises "InvalidArgument" if a "datetime" is passed as "min_value" or "max_value". Because "datetime" is a subclass of "date", such bound
"dates()" now raises "InvalidArgument" if a "datetime" is passed as "min_value" or "max_value". Because "datetime" is a subclass of "date", such bounds were previously accepted and then failed with a confusing "TypeError" while generating examples.
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.strategies.dates now raises InvalidArgument if a ~python:datetime.datetime is passed as min_value or max_value. Because datetime is a subclass of ~python:datetime.date, such bounds were previously accepted and then failed with a confusing TypeError while generating examples.
This patch removes a stray "print()" which fired whenever a "dates()" filter was rewritten.
This patch removes a stray "print()" which fired whenever a "dates()" filter was rewritten.
The canonical version of these notes (with links) is on readthedocs.
This patch removes a stray print() which fired whenever a |st.dates| filter was rewritten.
When using an alternative backend (such as hypothesis-crosshair), Hypothesis no longer emits a "test_case" observation for an iteration that the backe
When using an alternative backend (such as hypothesis-crosshair), Hypothesis no longer emits a "test_case" observation for an iteration that the backend aborts via "BackendCannotProceed" before the test body runs. Previously such an iteration -- for example when the crosshair backend has exhausted its search paths -- could surface as a spurious, draw-less "passed" observation with an empty representation, even though the engine already discards the iteration entirely.
The canonical version of these notes (with links) is on readthedocs.
This patch rewrites the internal date- and time-drawing helper to use plain arithmetic instead of branching on the values it draws. The generated dist
This patch rewrites the internal date- and time-drawing helper to use plain arithmetic instead of branching on the values it draws. The generated distribution is unchanged, but "dates()", "datetimes()", and "times()" are now much more efficient under symbolic-execution backends such as crosshair-tool, which can now solve for a specific date directly rather than enumerating candidates (issue #4759).
The canonical version of these notes (with links) is on readthedocs.
This patch rewrites the internal date- and time-drawing helper to use plain arithmetic instead of branching on the values it draws. The generated distribution is unchanged, but ~hypothesis.strategies.dates, ~hypothesis.strategies.datetimes, and ~hypothesis.strategies.times are now much more efficient under symbolic-execution backends such as crosshair-tool, which can now solve for a specific date directly rather than enumerating candidates (4759).
Shrinking large floats, strings, and bytestrings is now much faster in some cases (issue #4006).
Shrinking large floats, strings, and bytestrings is now much faster in some cases (issue #4006).
The canonical version of these notes (with links) is on readthedocs.
Shrinking large floats, strings, and bytestrings is now much faster in some cases (4006).
"from_dtype()" now supports the variable-width string dtype "numpy.dtypes.StringDType", generating arbitrary strings via "text()" (issue #4039).
"from_dtype()" now supports the variable-width string dtype "numpy.dtypes.StringDType", generating arbitrary strings via "text()" (issue #4039).
Additionally, passing a dtype class such as "np.dtypes.StringDType" where an instance like "np.dtypes.StringDType()" was expected now raises a clear error, rather than the previous confusing message (or silent coercion to the object dtype in "arrays()").
The canonical version of these notes (with links) is on readthedocs.
~hypothesis.extra.numpy.from_dtype now supports the variable-width string dtype numpy:numpy.dtypes.StringDType, generating arbitrary strings via ~hypothesis.strategies.text (4039).
Additionally, passing a dtype class such as np.dtypes.StringDType where an instance like np.dtypes.StringDType() was expected now raises a clear error, rather than the previous confusing message (or silent coercion to the object dtype in ~hypothesis.extra.numpy.arrays).
This patch improves the type annotations of "fixed_dictionaries()", which now accepts a "Mapping" rather than requiring an invariant "dict". Because t
This patch improves the type annotations of "fixed_dictionaries()", which now accepts a "Mapping" rather than requiring an invariant "dict". Because the value type is covariant, type-checkers can now infer the generated type even when the strategies are heterogeneous, e.g. a "mapping" annotated as "dict[str, SearchStrategy[int] | SearchStrategy[str]]" (issue #4665).
The "mapping" and "optional" arguments may now also have different key and value types, which are unioned in the inferred result.
The canonical version of these notes (with links) is on readthedocs.
This patch improves the type annotations of |st.fixed_dictionaries|, which now accepts a ~collections.abc.Mapping rather than requiring an invariant dict. Because the value type is covariant, type-checkers can now infer the generated type even when the strategies are heterogeneous, e.g. a mapping annotated as dict[str, SearchStrategy[int] | SearchStrategy[str]] (4665).
The mapping and optional arguments may now also have different key and value types, which are unioned in the inferred result.
This patch fixes a bug where resolving recursive forward references in "from_type()" (such as "A = list[Union["A", str]]", added in v6.152.11) could r
This patch fixes a bug where resolving recursive forward references in "from_type()" (such as "A = list[Union["A", str]]", added in v6.152.11) could recurse until it hit the interpreter's recursion limit before falling back to a deferred strategy. Because this depended on the ambient stack depth, it occasionally surfaced as a spurious "RecursionError" or other flaky failure. We now break the cycle eagerly by deferring, so resolution uses a small and constant amount of stack regardless of how deeply nested the reference is.
The canonical version of these notes (with links) is on readthedocs.
This patch fixes a bug where resolving recursive forward references in |st.from_type| (such as A = list[Union["A", str]], added in 6.152.11) could recurse until it hit the interpreter's recursion limit before falling back to a deferred strategy. Because this depended on the ambient stack depth, it occasionally surfaced as a spurious RecursionError or other flaky failure. We now break the cycle eagerly by deferring, so resolution uses a small and constant amount of stack regardless of how deeply nested the reference is.
"fixed_dictionaries()" now varies the iteration order of the dicts it generates, rather than always placing the required keys first, to help find bugs
"fixed_dictionaries()" now varies the iteration order of the dicts it generates, rather than always placing the required keys first, to help find bugs in code which is sensitive to key order (issue #3906). If you need a stable order, we recommend using "fixed_dictionaries(...).map(stable_sort_function)" or similar.
The canonical version of these notes (with links) is on readthedocs.
The "--hypothesis-show-statistics" report now accounts for the "Phase.explain" phase separately, rather than including its runtime and test cases in t
The "--hypothesis-show-statistics" report now accounts for the "Phase.explain" phase separately, rather than including its runtime and test cases in the "Phase.shrink" phase (issue #4179).
The canonical version of these notes (with links) is on readthedocs.
The --hypothesis-show-statistics report now accounts for the |Phase.explain| phase separately, rather than including its runtime and test cases in the |Phase.shrink| phase (4179).
Your coding agent can read these notes before it upgrades. Set up the MCP server →