Skip to content

Commit

Permalink
Ensure that IDs are treated case-insensitive in queries
Browse files Browse the repository at this point in the history
Under the hood this now creates and holds a lower-cased version of the ID
and always compares against that. The query tests have also been updated to
throw in some mixed-case IDs to test with.

See Textualize#1041 and Textualize#1047.
  • Loading branch information
davep committed Oct 31, 2022
1 parent 0d99b0c commit cad4a81
Show file tree
Hide file tree
Showing 3 changed files with 6 additions and 2 deletions.
2 changes: 1 addition & 1 deletion src/textual/css/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ def _check_class(self, node: DOMNode) -> bool:
return True

def _check_id(self, node: DOMNode) -> bool:
if not node.id == self._name_lower:
if (node._cmp_id is None) or (node._cmp_id.lower() != self._name_lower):
return False
if self.pseudo_classes and not node.has_pseudo_class(*self.pseudo_classes):
return False
Expand Down
2 changes: 2 additions & 0 deletions src/textual/dom.py
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,7 @@ def __init__(
self._classes = set()
self._name = name
self._id = None
self._cmp_id = None
if id is not None:
self.id = id

Expand Down Expand Up @@ -308,6 +309,7 @@ def id(self, new_id: str) -> str:
f"Node 'id' attribute may not be changed once set (current id={self._id!r})"
)
self._id = new_id
self._cmp_id = new_id.lower()
return new_id

@property
Expand Down
4 changes: 3 additions & 1 deletion tests/test_query.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ class App(Widget):
app._add_child(help_view)

widget1 = Widget(id="widget1")
widget2 = Widget(id="widget2")
widget2 = Widget(id="Widget2") # Note case.
sidebar = Widget(id="sidebar")
sidebar.add_class("float")

Expand Down Expand Up @@ -54,7 +54,9 @@ class App(Widget):
assert list(app.query("#main")) == [main_view]
assert list(app.query("View#main")) == [main_view]
assert list(app.query("#widget1")) == [widget1]
assert list(app.query("#Widget1")) == [widget1] # Note case.
assert list(app.query("#widget2")) == [widget2]
assert list(app.query("#Widget2")) == [widget2] # Note case.

assert list(app.query("Widget.float")) == [sidebar, tooltip, helpbar]
assert list(app.query(Widget).filter(".float")) == [sidebar, tooltip, helpbar]
Expand Down

0 comments on commit cad4a81

Please sign in to comment.