PyPI / hypothesis / 6.170.6

hypothesis 6.170.6

Source
https://github.com/HypothesisWorks/hypothesis
Artifact scanned
hypothesis-6.170.6.tar.gz (sdist · 506.1 KB · SHA-256 fc6a32aff0e0…)
Compared with
hypothesis-6.170.5.tar.gz (1 signals introduced since)
Files
114 scanned, 6 skipped (binary, oversized, or unrecognised)
Signals
0 critical · 0 warn · 34 info
Scan time
13.7 s
LLM review
Reviewed by claude-haiku-5-5 (Anthropic): 15 of 15 warn and critical signals; 15 demoted to info.
Disclude version
4.3.0
Scanned (UTC)
2026-10-23 14:12

Signals

Ordered by severity, then signals introduced in this release. Hidden characters are shown as ⟨U+…⟩.

  1. info warn → info by review dynamic-execution src/hypothesis/extra/ghostwriter.py:1841:13 new in this release

    `compile` called on a non-literal expression (ast pass, confidence 0.70)

                # executed; so you still shouldn't ghostwrite for hostile code.
                compile(identity_repr, "<string>", "exec")
            except SyntaxError:
                identity_repr = repr(identity_repr)
    dismissed LLM, confidence 0.90 Checks whether an identity repr is valid Python, falling back to repr on failure.
    Reasoning

    The code compiles identity_repr only to detect SyntaxError and falls back to repr. The comment notes that the module is not run, so this is a syntax probe.

  2. info warn → info by review frame-introspection src/hypothesis/control.py:50:13

    `inspect.currentframe` — call-stack frame introspection (ast pass, confidence 0.70)

            )
        frame = inspect.currentframe()
        where = _calling_function_location("reject", frame)
        if currently_in_test_context():
    likely benign LLM, confidence 0.95 Reads the caller's stack frame to record where reject() was called.
    Reasoning

    The frame is used only to locate the caller of reject() for error reporting and observability. This is ordinary test-framework behaviour with no network, exec or payload involved.

  3. info warn → info by review frame-introspection src/hypothesis/control.py:78:17

    `inspect.currentframe` — call-stack frame introspection (ast pass, confidence 0.70)

        if observability_enabled() or not condition:
            frame = inspect.currentframe()
            where = _calling_function_location("assume", frame)
            if observability_enabled() and currently_in_test_context():
    likely benign LLM, confidence 0.95 Reads the caller's stack frame to record where assume() was called.
    Reasoning

    Same pattern as the reject() call: the frame feeds a location string for assume() reporting, with no suspicious effect.

  4. info warn → info by review decoder-decompress-payload src/hypothesis/core.py:442:23

    file imports decoder module(s) base64, zlib and calls `.decompress()` — embedded payload decompressed at runtime (ast pass, confidence 0.75)

            try:
                decoded = zlib.decompress(decoded[1:])
            except zlib.error as err:
                raise InvalidArgument(
    likely benign LLM, confidence 0.90 Base64-decodes and zlib-decompresses a reproduction blob supplied to reproduce_failure.
    Reasoning

    This is the decoder for Hypothesis's reproduce_failure blob: a base64 string with a version byte followed by zlib data. The decompressed bytes are parsed as recorded choices, not executed, so it is a legitimate serialization format.

  5. info warn → info by review dynamic-execution src/hypothesis/extra/ghostwriter.py:293:17

    `compile` called on a non-literal expression (ast pass, confidence 0.70)

                with contextlib.suppress(SyntaxError):
                    compile(repr(st.just(param.default)), "<string>", "eval")
                    elements.insert(0, param.default)
            if elements or types:
    dismissed LLM, confidence 0.90 Checks that a parameter default's repr is valid Python syntax.
    Reasoning

    compile() is used only as a syntax-validity check on a repr string inside a suppress(SyntaxError) block. The result is never run.

  6. info warn → info by review dynamic-execution src/hypothesis/extra/ghostwriter.py:719:9

    `compile` called on a non-literal expression (ast pass, confidence 0.70)

            r = re.sub(r"(lambda.*?: )(<unknown>)([,)])", r"\1...\3", r)
            compile(r, "<string>", "eval")
            # Finally, try to work out the imports we need for builds(), .map(),
            # .filter(), and .flatmap() to work without NameError
    dismissed LLM, confidence 0.90 Validates generated strategy source as a Python expression.
    Reasoning

    compile(r, ..., 'eval') validates generated source text as an expression before further processing. It is a syntax check, not execution of untrusted input.

  7. identifier `aᵏ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # The sum of a geometric series is given by (ref: wikipedia):
        #     ᵐ∑ₖ₌₀ aᵏ = (aᵐ⁺¹ - 1) / (a - 1)
        #               = S(m) / S(0)
        # assuming a != 1 and using the definition
  8. identifier `aᵐ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # The sum of a geometric series is given by (ref: wikipedia):
        #     ᵐ∑ₖ₌₀ aᵏ = (aᵐ⁺¹ - 1) / (a - 1)
        #               = S(m) / S(0)
        # assuming a != 1 and using the definition
  9. identifier `aᵐ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # assuming a != 1 and using the definition
        #         S(m) := aᵐ⁺¹ - 1.
        # The sum we want, starting from a number n [0 <= n <= m] rather than zero, is
        #     ᵐ∑ₖ₌ₙ aᵏ = ᵐ∑ₖ₌₀ aᵏ - ⁿ⁻¹∑ₖ₌₀ aᵏ = S(m) / S(0) - S(n - 1) / S(0)
  10. identifier `aᵏ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # The sum we want, starting from a number n [0 <= n <= m] rather than zero, is
        #     ᵐ∑ₖ₌ₙ aᵏ = ᵐ∑ₖ₌₀ aᵏ - ⁿ⁻¹∑ₖ₌₀ aᵏ = S(m) / S(0) - S(n - 1) / S(0)
        def S(n):
            return alphabet_size ** (n + 1) - 1
  11. identifier `aᵏ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # The sum we want, starting from a number n [0 <= n <= m] rather than zero, is
        #     ᵐ∑ₖ₌ₙ aᵏ = ᵐ∑ₖ₌₀ aᵏ - ⁿ⁻¹∑ₖ₌₀ aᵏ = S(m) / S(0) - S(n - 1) / S(0)
        def S(n):
            return alphabet_size ** (n + 1) - 1
  12. identifier `aᵏ` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # The sum we want, starting from a number n [0 <= n <= m] rather than zero, is
        #     ᵐ∑ₖ₌ₙ aᵏ = ᵐ∑ₖ₌₀ aᵏ - ⁿ⁻¹∑ₖ₌₀ aᵏ = S(m) / S(0) - S(n - 1) / S(0)
        def S(n):
            return alphabet_size ** (n + 1) - 1
  13. info warn → info by review frame-introspection src/hypothesis/internal/conjecture/junkdrawer.py:316:13

    `sys._getframe` — call-stack frame introspection (ast pass, confidence 0.70)

        """
        frame = sys._getframe(2)
        size = 1
        while frame:
    likely benign LLM, confidence 0.90 Walks the call stack to compute a frame-depth size value.
    Reasoning

    sys._getframe(2) walks the call stack to measure its depth for a size estimate. This is a common internal technique with no harmful effect.

  14. identifier `ˆøπ` mixes scripts: Other + Latin + Greek (in string/comment) (raw pass, confidence 0.40)

        # common unicode characters
        "Ω≈ç√∫˜µ≤≥÷åß∂ƒ©˙∆˚¬…æœ∑´®†¥¨ˆøπ“‘¡™£¢∞§¶•ªº–≠¸˛Ç◊ı˜Â¯˘¿ÅÍÎÏ˝ÓÔ⟨U+F8FF⟩ÒÚÆ☃Œ„´‰ˇÁ¨ˆØ∏”’`⁄€‹›fifl‡°·‚—±",
        # characters which increase in length when lowercased
  15. identifier `ˇÁ` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # common unicode characters
        "Ω≈ç√∫˜µ≤≥÷åß∂ƒ©˙∆˚¬…æœ∑´®†¥¨ˆøπ“‘¡™£¢∞§¶•ªº–≠¸˛Ç◊ı˜Â¯˘¿ÅÍÎÏ˝ÓÔ⟨U+F8FF⟩ÒÚÆ☃Œ„´‰ˇÁ¨ˆØ∏”’`⁄€‹›fifl‡°·‚—±",
        # characters which increase in length when lowercased
  16. identifier `ˆØ` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # common unicode characters
        "Ω≈ç√∫˜µ≤≥÷åß∂ƒ©˙∆˚¬…æœ∑´®†¥¨ˆøπ“‘¡™£¢∞§¶•ªº–≠¸˛Ç◊ı˜Â¯˘¿ÅÍÎÏ˝ÓÔ⟨U+F8FF⟩ÒÚÆ☃Œ„´‰ˇÁ¨ˆØ∏”’`⁄€‹›fifl‡°·‚—±",
        # characters which increase in length when lowercased
  17. identifier `æœÆŒffʤʨß` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

        # ligatures
        "æœÆŒffʤʨß",
        # emoticons
        "(╯°□°)╯︵ ┻━┻)",
  18. identifier `ʇǝɯɐ` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # upsidown text
        "ʇǝɯɐ ʇᴉs ɹolop ɯnsdᴉ ɯǝɹo˥",
        # reserved strings in windows
        "NUL",
  19. identifier `ʇᴉs` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # upsidown text
        "ʇǝɯɐ ʇᴉs ɹolop ɯnsdᴉ ɯǝɹo˥",
        # reserved strings in windows
        "NUL",
  20. identifier `ɹolop` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # upsidown text
        "ʇǝɯɐ ʇᴉs ɹolop ɯnsdᴉ ɯǝɹo˥",
        # reserved strings in windows
        "NUL",
  21. identifier `ɯnsdᴉ` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # upsidown text
        "ʇǝɯɐ ʇᴉs ɹolop ɯnsdᴉ ɯǝɹo˥",
        # reserved strings in windows
        "NUL",
  22. identifier `ɯǝɹo` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

        # upsidown text
        "ʇǝɯɐ ʇᴉs ɹolop ɯnsdᴉ ɯǝɹo˥",
        # reserved strings in windows
        "NUL",
  23. identifier `ͅi` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

    �̲e͇̣̰̦̬͎ ̢̼̻̱̘h͚͎͙̜̣̲ͅi̦̲̣̰̤v̻͍e̺̭̳̪̰-m̢iͅn̖̺̞̲̯̰d̵̼̟͙̩̼̘̳ ̞̥̱̳̭r̛̗̘e͙p͠r̼̞̻̭̗e̺̠̣͟s̘͇̳͍̝͉e͉̥̯̞̲͚̬͜ǹ̬͎͎̟̖͇̤t͍̬̤͓̼̭͘ͅi̪̱n͠g̴͉ ⟨U+034F⟩͉ͅc̬̟h͡a̫̻̯͘o̫̟̖͍̙̝͉s̗̦̲.̨̹͈̣",
  24. identifier `iͅn` mixes scripts: Latin + Other (in string/comment) (raw pass, confidence 0.40)

    �̜̣̲ͅi̦̲̣̰̤v̻͍e̺̭̳̪̰-m̢iͅn̖̺̞̲̯̰d̵̼̟͙̩̼̘̳ ̞̥̱̳̭r̛̗̘e͙p͠r̼̞̻̭̗e̺̠̣͟s̘͇̳͍̝͉e͉̥̯̞̲͚̬͜ǹ̬͎͎̟̖͇̤t͍̬̤͓̼̭͘ͅi̪̱n͠g̴͉ ⟨U+034F⟩͉ͅc̬̟h͡a̫̻̯͘o̫̟̖͍̙̝͉s̗̦̲.̨̹͈̣",
  25. identifier `ͅi` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

    �̲͚̬͜ǹ̬͎͎̟̖͇̤t͍̬̤͓̼̭͘ͅi̪̱n͠g̴͉ ⟨U+034F⟩͉ͅc̬̟h͡a̫̻̯͘o̫̟̖͍̙̝͉s̗̦̲.̨̹͈̣",
  26. identifier `ͅc` mixes scripts: Other + Latin (in string/comment) (raw pass, confidence 0.40)

    �͇̤t͍̬̤͓̼̭͘ͅi̪̱n͠g̴͉ ⟨U+034F⟩͉ͅc̬̟h͡a̫̻̯͘o̫̟̖͍̙̝͉s̗̦̲.̨̹͈̣",
  27. info warn → info by review frame-introspection src/hypothesis/internal/coverage.py:74:18

    `sys._getframe` — call-stack frame introspection (ast pass, confidence 0.70)

            # stack frames up.
            caller = sys._getframe(depth + 2)
            fname = pretty_file_name(caller.f_code.co_filename)
            local_description = f"{name} at {fname}:{caller.f_lineno}"
    likely benign LLM, confidence 0.90 Reads the caller frame to label a coverage entry with file and line.
    Reasoning

    The frame is used to label coverage-collection entries with the caller's file and line. This is internal bookkeeping for the library's own coverage reporting.

  28. info warn → info by review dynamic-execution src/hypothesis/internal/lambda_sources.py:265:20

    `eval` called on a non-literal expression (ast pass, confidence 0.70)

        if not f_code.co_freevars and not referenced_modules:
            compiled = eval(source, f_globals)
        else:
            if f_code.co_freevars:
    likely benign LLM, confidence 0.85 Evaluates reconstructed lambda source to rebuild a callable.
    Reasoning

    The eval reconstructs a lambda from source the library extracted from the user's own code, to recover a callable for display and reproduction. The input is the project's own source, not attacker-controlled data.

  29. info warn → info by review dynamic-execution src/hypothesis/internal/lambda_sources.py:298:9

    `exec` called on a non-literal expression (ast pass, confidence 0.70)

            )
            exec(exec_str, f_globals)
            compiled = f_globals["__construct_lambda"]()
    likely benign LLM, confidence 0.85 Executes a generated wrapper to reconstruct a lambda with closure variables.
    Reasoning

    The exec builds a wrapper function that rebuilds a lambda with its closure variables, from source derived from the user's code. It is a known technique for lambda reconstruction, and no network or process activity is involved.

  30. info warn → info by review dynamic-execution src/hypothesis/internal/reflection.py:367:5

    `exec` called on a non-literal expression (ast pass, confidence 0.70)

        assert isinstance(source, str)
        exec(source, result.__dict__)
        eval_cache[source] = result
        return result
    likely benign LLM, confidence 0.80 Executes reconstructed function source into a fresh namespace and caches the result.
    Reasoning

    Source text, which comes from the project's own functions, is exec'd into a fresh namespace and cached by source string. This is reflection machinery for rebuilding callables, with no evident malicious behaviour.

  31. info warn → info by review frame-introspection src/hypothesis/internal/scrutineer.py:114:13

    `sys.settrace` — call-stack frame introspection (ast pass, confidence 0.70)

            if not hasattr(sys, "monitoring"):  # pragma: no cover  # only on Python < 3.12
                sys.settrace(self.trace)
                return self
    likely benign LLM, confidence 0.90 Installs a trace function on Python versions before 3.12 for coverage analysis.
    Reasoning

    sys.settrace installs the library's own tracer for branch and coverage analysis on pre-3.12 Python, guarded by a version check. This is a legitimate profiling mechanism.

  32. info warn → info by review frame-introspection src/hypothesis/internal/scrutineer.py:137:13

    `sys.settrace` — call-stack frame introspection (ast pass, confidence 0.70)

            if not hasattr(sys, "monitoring"):  # pragma: no cover  # only on Python < 3.12
                sys.settrace(None)
                return
    likely benign LLM, confidence 0.90 Removes the trace function installed for coverage analysis.
    Reasoning

    This is the matching teardown of the tracer installed earlier, clearing it with settrace(None). It is paired cleanup for legitimate tracing.

  33. info warn → info by review frame-introspection src/hypothesis/strategies/_internal/strategies.py:103:31

    `sys._getframe` — call-stack frame introspection (ast pass, confidence 0.70)

            return location
        frame: FrameType | None = sys._getframe(1)
        while frame is not None and is_hypothesis_file(frame.f_code.co_filename):
            frame = frame.f_back
    likely benign LLM, confidence 0.95 Walks the stack past library frames to find the user's call site.
    Reasoning

    The loop walks up the stack past Hypothesis's own files to find the user's calling location, for error messages. It is benign introspection.

  34. info warn → info by review frame-introspection src/hypothesis/strategies/_internal/types.py:227:37

    `sys._getframe` — call-stack frame introspection (ast pass, confidence 0.70)

        found_loc: str | None = None
        frame: types.FrameType | None = sys._getframe()
        while frame is not None:
            loc = f"{frame.f_code.co_filename}:{frame.f_lineno}"
    likely benign LLM, confidence 0.93 Hypothesis walks the call stack via sys._getframe to record the source location where a type strategy was created.
    Reasoning

    sys._getframe is used to walk the call stack and locate the user-code frame that defined a strategy, for reporting purposes. This is a standard debugging/introspection technique in a property-testing library (Hypothesis), with no network, decoding, or execution of dynamic code. The snippet reads frame metadata only, so the finding is a legitimate pattern.

Reproduce This Scan

Run disclude locally to verify. These commands scan the published file; the "new in this release" marks come from comparing it with the previous release's file, which they don't repeat. Add --format sarif for SARIF output. Add --llm (with an API key in the environment) to include the LLM review.

cargo install disclude --version 4.3.0
curl -fsSL -o hypothesis-6.170.6.tar.gz https://files.pythonhosted.org/packages/05/a8/c290eb70e3d6d8e39d2d93556812bbcfc4269b839239505b246cf276e747/hypothesis-6.170.6.tar.gz
printf '%s  %s\n' fc6a32aff0e042dd2d844b9cbf18346761835668025e40a9cc01d5c706e73285 hypothesis-6.170.6.tar.gz | shasum -a 256 -c -
mkdir pkg && tar -xzf hypothesis-6.170.6.tar.gz -C pkg --strip-components 1
disclude scan --untrusted --severity info pkg