Support for binding/evaluating XPath variables.
This commit is contained in:
parent
5a0e8c5480
commit
ad34ab47a0
|
@ -45,13 +45,29 @@ module Oga
|
|||
# For more information on the specification, see
|
||||
# <http://www.w3.org/TR/xpath/#numbers>.
|
||||
#
|
||||
# ## Variables
|
||||
#
|
||||
# The evaluator supports the binding of custom variables in the
|
||||
# {#initialize} method. Variables can be bound by passing in a Hash with the
|
||||
# keys set to the variable names (minus the `$` sign) and their values to
|
||||
# the variable values. The keys of the variables Hash *must* be Strings.
|
||||
#
|
||||
# A basic example:
|
||||
#
|
||||
# evaluator = Evaluator.new(document, 'number' => 10)
|
||||
#
|
||||
# evaluator.evaluate('$number') # => 10
|
||||
#
|
||||
class Evaluator
|
||||
##
|
||||
# @param [Oga::XML::Document|Oga::XML::Node] document
|
||||
# @param [Hash] variables Hash containing variables to expose to the XPath
|
||||
# expressions.
|
||||
#
|
||||
def initialize(document)
|
||||
def initialize(document, variables = {})
|
||||
@document = document
|
||||
@nodes = []
|
||||
@variables = variables
|
||||
end
|
||||
|
||||
##
|
||||
|
@ -1490,6 +1506,25 @@ module Oga
|
|||
return ast_node.children[0]
|
||||
end
|
||||
|
||||
##
|
||||
# Processes a variable reference. If the variable is not defined an error
|
||||
# is raised.
|
||||
#
|
||||
# @param [Oga::XPath::Node] ast_node
|
||||
# @param [Oga::XML::NodeSet] context
|
||||
# @return [Mixed]
|
||||
# @raise [RuntimeError]
|
||||
#
|
||||
def on_var(ast_node, context)
|
||||
name = ast_node.children[0]
|
||||
|
||||
if @variables.key?(name)
|
||||
return @variables[name]
|
||||
else
|
||||
raise "Undefined XPath variable: #{name}"
|
||||
end
|
||||
end
|
||||
|
||||
##
|
||||
# Returns the node for a function call. This node is either the first node
|
||||
# in the supplied node set, or the first node in the current context.
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
require 'spec_helper'
|
||||
|
||||
describe Oga::XPath::Evaluator do
|
||||
context 'variable bindings' do
|
||||
before do
|
||||
@document = parse('<a></a>')
|
||||
end
|
||||
|
||||
example 'evaluate a variable' do
|
||||
evaluator = described_class.new(@document, 'number' => 10.0)
|
||||
|
||||
evaluator.evaluate('$number').should == 10.0
|
||||
end
|
||||
|
||||
example 'raise RuntimeError when evaluating an unbound variable' do
|
||||
evaluator = described_class.new(@document)
|
||||
block = lambda { evaluator.evaluate('$number') }
|
||||
|
||||
block.should raise_error 'Undefined XPath variable: number'
|
||||
end
|
||||
end
|
||||
end
|
Loading…
Reference in New Issue