lib/xpath/renderer.rb in xpath-2.0.0 vs lib/xpath/renderer.rb in xpath-2.1.0
- old
+ new
@@ -36,55 +36,43 @@
def this_node
'.'
end
- def descendant(parent, element_names)
- if element_names.length == 1
- "#{parent}//#{element_names.first}"
- elsif element_names.length > 1
- "#{parent}//*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
- else
- "#{parent}//*"
- end
+ def descendant(current, element_names)
+ with_element_conditions("#{current}//", element_names)
end
- def child(parent, element_names)
- if element_names.length == 1
- "#{parent}/#{element_names.first}"
- elsif element_names.length > 1
- "#{parent}/*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
- else
- "#{parent}/*"
- end
+ def child(current, element_names)
+ with_element_conditions("#{current}/", element_names)
end
- def axis(parent, name, tag_name)
- "#{parent}/#{name}::#{tag_name}"
+ def axis(current, name, element_names)
+ with_element_conditions("#{current}/#{name}::", element_names)
end
- def node_name(current)
- "name(#{current})"
+ def anywhere(element_names)
+ with_element_conditions("//", element_names)
end
def where(on, condition)
"#{on}[#{condition}]"
end
def attribute(current, name)
"#{current}/@#{name}"
end
- def equality(one, two)
- "#{one} = #{two}"
+ def binary_operator(name, left, right)
+ "(#{left} #{name} #{right})"
end
def is(one, two)
if @type == :exact
- equality(one, two)
+ binary_operator("=", one, two)
else
- contains(one, two)
+ function(:contains, one, two)
end
end
def variable(name)
"%{#{name}}"
@@ -92,14 +80,10 @@
def text(current)
"#{current}/text()"
end
- def normalized_space(current)
- "normalize-space(#{current})"
- end
-
def literal(node)
node
end
def css(current, selector)
@@ -111,64 +95,22 @@
def union(*expressions)
expressions.join(' | ')
end
- def anywhere(element_names)
- if element_names.length == 1
- "//#{element_names.first}"
- elsif element_names.length > 1
- "//*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
- else
- "//*"
- end
+ def function(name, *arguments)
+ "#{name}(#{arguments.join(", ")})"
end
- def contains(current, value)
- "contains(#{current}, #{value})"
- end
+ private
- def starts_with(current, value)
- "starts-with(#{current}, #{value})"
- end
-
- def and(one, two)
- "(#{one} and #{two})"
- end
-
- def or(one, two)
- "(#{one} or #{two})"
- end
-
- def one_of(current, values)
- values.map { |value| "#{current} = #{value}" }.join(' or ')
- end
-
- def next_sibling(current, element_names)
+ def with_element_conditions(expression, element_names)
if element_names.length == 1
- "#{current}/following-sibling::*[1]/self::#{element_names.first}"
+ "#{expression}#{element_names.first}"
elsif element_names.length > 1
- "#{current}/following-sibling::*[1]/self::*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
+ "#{expression}*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
else
- "#{current}/following-sibling::*[1]/self::*"
+ "#{expression}*"
end
- end
-
- def previous_sibling(current, element_names)
- if element_names.length == 1
- "#{current}/preceding-sibling::*[1]/self::#{element_names.first}"
- elsif element_names.length > 1
- "#{current}/preceding-sibling::*[1]/self::*[#{element_names.map { |e| "self::#{e}" }.join(" | ")}]"
- else
- "#{current}/preceding-sibling::*[1]/self::*"
- end
- end
-
- def inverse(current)
- "not(#{current})"
- end
-
- def string_function(current)
- "string(#{current})"
end
end
end