XPathContext
is the entry point for searching a Document
by using XPath
.
static VALUE new (VALUE klass, VALUE nodeobj) { xmlNodePtr node; xmlXPathContextPtr ctx; VALUE self; Data_Get_Struct(nodeobj, xmlNode, node); xmlXPathInit(); ctx = xmlXPathNewContext(node->doc); ctx->node = node; xmlXPathRegisterNs(ctx, NOKOGIRI_BUILTIN_PREFIX, NOKOGIRI_BUILTIN_URI); xmlXPathRegisterFuncNS(ctx, (const xmlChar *)"css-class", NOKOGIRI_BUILTIN_URI, xpath_builtin_css_class); xmlXPathRegisterFuncNS(ctx, (const xmlChar *)"local-name-is", NOKOGIRI_BUILTIN_URI, xpath_builtin_local_name_is); self = Data_Wrap_Struct(klass, 0, deallocate, ctx); return self; }
Create a new XPathContext
with node
as the reference point.
static VALUE evaluate(int argc, VALUE *argv, VALUE self) { VALUE search_path, xpath_handler; VALUE retval = Qnil; xmlXPathContextPtr ctx; xmlXPathObjectPtr xpath; xmlChar *query; Data_Get_Struct(self, xmlXPathContext, ctx); if (rb_scan_args(argc, argv, "11", &search_path, &xpath_handler) == 1) { xpath_handler = Qnil; } query = (xmlChar *)StringValueCStr(search_path); if (Qnil != xpath_handler) { /* FIXME: not sure if this is the correct place to shove private data. */ ctx->userData = (void *)xpath_handler; xmlXPathRegisterFuncLookup(ctx, lookup, (void *)xpath_handler); } xmlResetLastError(); xmlSetStructuredErrorFunc(NULL, Nokogiri_error_raise); /* For some reason, xmlXPathEvalExpression will blow up with a generic error */ /* when there is a non existent function. */ xmlSetGenericErrorFunc(NULL, xpath_generic_exception_handler); xpath = xmlXPathEvalExpression(query, ctx); xmlSetStructuredErrorFunc(NULL, NULL); xmlSetGenericErrorFunc(NULL, NULL); if (xpath == NULL) { xmlErrorPtr error = xmlGetLastError(); rb_exc_raise(Nokogiri_wrap_xml_syntax_error(error)); } retval = xpath2ruby(xpath, ctx); if (retval == Qundef) { retval = noko_xml_node_set_wrap(NULL, DOC_RUBY_OBJECT(ctx->doc)); } xmlXPathFreeNodeSetList(xpath); return retval; }
Evaluate the search_path
returning an XML::XPath
object.
# File lib/nokogiri/xml/xpath_context.rb, line 8 def register_namespaces(namespaces) namespaces.each do |k, v| k = k.to_s.gsub(/.*:/, "") # strip off 'xmlns:' or 'xml:' register_ns(k, v) end end
Register namespaces in namespaces
static VALUE register_ns(VALUE self, VALUE prefix, VALUE uri) { xmlXPathContextPtr ctx; Data_Get_Struct(self, xmlXPathContext, ctx); xmlXPathRegisterNs(ctx, (const xmlChar *)StringValueCStr(prefix), (const xmlChar *)StringValueCStr(uri) ); return self; }
Register the namespace with prefix
and uri
.
static VALUE register_variable(VALUE self, VALUE name, VALUE value) { xmlXPathContextPtr ctx; xmlXPathObjectPtr xmlValue; Data_Get_Struct(self, xmlXPathContext, ctx); xmlValue = xmlXPathNewCString(StringValueCStr(value)); xmlXPathRegisterVariable(ctx, (const xmlChar *)StringValueCStr(name), xmlValue ); return self; }
Register the variable name
with value
.
© 2008–2018 Aaron Patterson, Mike Dalessio, Charles Nutter, Sergio Arbeo,
Patrick Mahoney, Yoko Harada, Akinori MUSHA, John Shahid, Lars Kanis
Licensed under the MIT License.
https://nokogiri.org/rdoc/Nokogiri/XML/XPathContext.html