From 213f391bce63fcc708a5aeb3a146b0cc0b6c1f13 Mon Sep 17 00:00:00 2001 From: Maarten Breddels Date: Fri, 23 Oct 2026 14:11:54 +0200 Subject: [PATCH 1/2] Give implements a return type, so checkers see typed widget calls implements() had no return annotation. ty does not infer return types of installed packages, so every function built with it, such as all of ipyvuetify.components and reacton.ipywidgets, returned Any or Unknown. A call like solara.v.Btn(...) was therefore never checked. With the annotation, ty reveals solara.v.Btn(...) as ValueElement[Btn, Any]. A ty run over the GrottoAI leasing app with this change still passes. mypy gives the same two errors as on master. Co-Authored-By: Claude Opus 5.5 --- reacton/utils.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reacton/utils.py b/reacton/utils.py index f11c0d3..a66b6c4 100644 --- a/reacton/utils.py +++ b/reacton/utils.py @@ -19,7 +19,7 @@ def without_default(func: Callable, kwargs): return non_default_kwargs -def implements(f: Callable[P, T]): +def implements(f: Callable[P, T]) -> Callable[[Callable], Callable[P, T]]: def caster(fimpl: Callable) -> Callable[P, T]: # wraps gives us the right signature at runtime (such as Jupyter) return cast(Callable[P, T], functools.wraps(f)(fimpl)) From 7dd553583f5072208f88a1c4b105e19934d78b63 Mon Sep 17 00:00:00 2001 From: Maarten Breddels Date: Fri, 23 Oct 2026 14:25:14 +0200 Subject: [PATCH 2/2] Use the real Button argument in the equals test With implements typed, mypy now checks the arguments of w.Button. The test passed label=..., but ipywidgets Button has no label argument, so the element held a keyword the widget never uses. The test only checks equality, so it passed at runtime. description is the argument that sets the button text. Co-Authored-By: Claude Opus 5.5 --- reacton/utils_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reacton/utils_test.py b/reacton/utils_test.py index 646d0dd..d3bfd74 100644 --- a/reacton/utils_test.py +++ b/reacton/utils_test.py @@ -118,7 +118,7 @@ def make_el(a): def on_click(): pass - return w.Button(on_click=on_click, label=f"{a}") + return w.Button(on_click=on_click, description=f"{a}") el1 = make_el(1) el2 = make_el(1)