Repository: HypothesisWorks/hypothesis

Issue:
`AttributeError` on serializing defaults in lambdas
I believe there is a typo on this [line](https://github.com/HypothesisWorks/hypothesis/blob/master/hypothesis-python/src/hypothesis/internal/lambda_sources.py#L89) that leads to an `AttributeError`:

```
            if len(consts_repr) > 48:
                consts_repr = hashlib.sha384(consts_repr.encode()).digest()
            if len(defaults_repr) > 48:
>               defaults_repr = hashlib.sha384(consts_repr.encode()).digest()
                                               ^^^^^^^^^^^^^^^^^^
E               AttributeError: 'bytes' object has no attribute 'encode'. Did you mean: 'decode'?
```

It should be this instead.

```python
defaults_repr = hashlib.sha384(defaults_repr.encode()).digest()
```

Found in [one](https://github.com/schemathesis/schemathesis/actions/runs/17364134419/job/49288267686) of the Schemathesis tests. Though I have no minimal reproducer but I think the typo is apparent.

Btw, locally, `pyright` highlighted the issue - is there something preventing mypy from detecting it in Hypothesis CI?


Discussion:
Indeed it should! Thanks for reporting, I'll put up a fix in short order.



Patch:
diff --git a/hypothesis-python/RELEASE.rst b/hypothesis-python/RELEASE.rst
new file mode 100644
index 0000000000..28c76d96fa
--- /dev/null
+++ b/hypothesis-python/RELEASE.rst
@@ -0,0 +1,4 @@
+RELEASE_TYPE: patch
+
+Fix a typo affecting pretty-printing of lambdas with complex default
+arguments.
diff --git a/hypothesis-python/src/hypothesis/internal/lambda_sources.py b/hypothesis-python/src/hypothesis/internal/lambda_sources.py
index 5cb1862a09..0c099183a0 100644
--- a/hypothesis-python/src/hypothesis/internal/lambda_sources.py
+++ b/hypothesis-python/src/hypothesis/internal/lambda_sources.py
@@ -86,7 +86,7 @@ def _function_key(f, *, bounded_size=False):
         if len(consts_repr) > 48:
             consts_repr = hashlib.sha384(consts_repr.encode()).digest()
         if len(defaults_repr) > 48:
-            defaults_repr = hashlib.sha384(consts_repr.encode()).digest()
+            defaults_repr = hashlib.sha384(defaults_repr.encode()).digest()
     return (
         consts_repr,
         defaults_repr,


Test patch:
diff --git a/hypothesis-python/tests/cover/test_reflection.py b/hypothesis-python/tests/cover/test_reflection.py
index 9be89325d0..fc12fcd50b 100644
--- a/hypothesis-python/tests/cover/test_reflection.py
+++ b/hypothesis-python/tests/cover/test_reflection.py
@@ -752,12 +752,12 @@ def test_is_unrecognized_identity(f):
 
 
 def test_cache_key_size_is_bounded():
-    # Modify co_consts because ("a" * 1000) may not be evaluated at compile time
-    f = lambda: "a"
+    # Modify co_consts because ("c" * 1000) may not be evaluated at compile time
+    f = lambda x="a" * 1000, *, y="b" * 1000: "c"
     f.__code__ = f.__code__.replace(
-        co_consts=tuple(c * 1000 if c == "a" else c for c in f.__code__.co_consts)
+        co_consts=tuple(c * 1000 if c == "c" else c for c in f.__code__.co_consts)
     )
-    assert len(repr(lambda_sources._function_key(f))) > 1000
+    assert len(repr(lambda_sources._function_key(f))) > 3000
     assert len(repr(lambda_sources._function_key(f, bounded_size=True))) < 1000