Skip to content

Commit

Permalink
fix xpath translating for > combinator
Browse files Browse the repository at this point in the history
  • Loading branch information
annbgn committed Aug 17, 2021
1 parent 0e37bf2 commit 1f8ddd1
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 6 deletions.
15 changes: 11 additions & 4 deletions cssselect/xpath.py
Original file line number Diff line number Diff line change
Expand Up @@ -76,14 +76,21 @@ def add_star_prefix(self):
"""
self.path += "*/"

def join(self, combiner, other, closing_combiner=None):
def join(self, combiner, other, closing_combiner=None, has_inner_condition=False):
path = _unicode(self) + combiner
# Any "star prefix" is redundant when joining.
if other.path != "*/":
path += other.path
self.path = path
self.element = other.element + closing_combiner if closing_combiner else other.element
self.condition = other.condition
if not has_inner_condition:
self.element = other.element + closing_combiner if closing_combiner else other.element
self.condition = other.condition
else:
self.element = other.element
if other.condition:
self.element += "[" + other.condition + "]"
if closing_combiner:
self.element += closing_combiner
return self


Expand Down Expand Up @@ -390,7 +397,7 @@ def xpath_indirect_adjacent_combinator(self, left, right):

def xpath_relation_descendant_combinator(self, left, right):
"""right is a child, grand-child or further descendant of left; select left"""
return left.join("[descendant::", right, closing_combiner="]")
return left.join("[descendant::", right, closing_combiner="]", has_inner_condition=True)

def xpath_relation_child_combinator(self, left, right):
"""right is an immediate child of left; select left"""
Expand Down
4 changes: 2 additions & 2 deletions tests/test_cssselect.py
Original file line number Diff line number Diff line change
Expand Up @@ -469,8 +469,8 @@ def xpath(css):
assert xpath("e:root") == ("e[not(parent::*)]")
assert xpath("e:hover") == ("e[0]") # never matches
assert (
xpath("div:has(div.foo)") == "div[descendant::div]"
"[@class and contains(concat(' ', normalize-space(@class), ' '), ' foo ')]"
xpath("div:has(bar.foo)")
== "div[descendant::bar[@class and contains(concat(' ', normalize-space(@class), ' '), ' foo ')]]"
)
assert xpath("e:has(> f)") == "e[./f]"
assert xpath("e:has(f)") == "e[descendant::f]"
Expand Down

0 comments on commit 1f8ddd1

Please sign in to comment.