Textualize/textual · error · WrongType
Descendant with id={id!r} is the wrong type; expected type {
Error message
Descendant with id={id!r} is the wrong type; expected type {expect_type.__name__!r}, found {widget} What it means
Deep lookup variant: get_widget_by_id uses query_one('#id') and then checks expect_type; WrongType signals the descendant exists but is not the expected type.
Source
Thrown at src/textual/widget.py:1149
"""Return the first descendant widget with the given ID.
Performs a depth-first search rooted at this widget.
Args:
id: The ID to search for in the subtree.
expect_type: Require the object be of the supplied type, or None for any type.
Returns:
The first descendant encountered with this ID.
Raises:
NoMatches: if no children could be found for this ID.
WrongType: if the wrong type was found.
"""
widget = self.query_one(f"#{id}")
if expect_type is not None and not isinstance(widget, expect_type):
raise WrongType(
f"Descendant with id={id!r} is the wrong type; expected type {expect_type.__name__!r}, found {widget}"
)
return widget
def get_child_by_type(self, expect_type: type[ExpectType]) -> ExpectType:
"""Get the first immediate child of a given type.
Only returns exact matches, and so will not match subclasses of the given type.
Args:
expect_type: The type of the child to search for.
Raises:
NoMatches: If no matching child is found.
Returns:
The first immediate child widget with the expected type.
"""View on GitHub (pinned to 06dbeef4bb)
Solutions
- Align expect_type with the actual widget type
- Rename ids so each type has a distinct id
- Use query_one with a compound selector like "#footer.footer-class"
Example fix
# before
w = self.get_widget_by_id("footer", expect_type=Footer)
# after
w = self.get_widget_by_id("footer", expect_type=MyCustomFooter) Defensive patterns
Strategy: type-guard
Validate before calling
widget = self.query_one(f"#{id}")
if isinstance(widget, expect_type):
use(widget) Type guard
def descendant_is_type(root: Widget, id: str, t: type) -> bool:
return isinstance(root.query_one(f"#{id}"), t) Try / catch
try:
w = self.get_widget_by_id("x", expect_type=T)
except WrongType:
w = self.query_one("#x") # handle actual type Prevention
- Give distinct ids per widget type
- Keep selectors and widget classes aligned during refactors
When it happens
Trigger: get_widget_by_id("footer", expect_type=Footer) where a different widget type holds that id somewhere in the subtree.
Common situations: Reusing an id across different screens/layouts after refactors; custom replacements for stock widgets keeping the same id.
Related errors
- Query value is the wrong type; expected type {expect_type.__
- Query value is the wrong type; expected type {expect_type.__
- Node matching {query_selector!r} is the wrong type; expected
- Child with id={id!r} is the wrong type; expected type {expec
- No immediate child of type {expect_type}; {self._nodes}
AI-assisted analysis of Textualize/textual@06dbeef4bb (2026-08-27).
Data as JSON: /api/errors/2b363cca7a62953b.
Report an issue: GitHub.