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; xmlXPathInit(); Data_Get_Struct(nodeobj, xmlNode, node); ctx = xmlXPathNewContext(node->doc); ctx->node = node; self = Data_Wrap_Struct(klass, 0, deallocate, ctx); /*rb_iv_set(self, "@xpath_handler", Qnil); */ 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 thing = 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)); } assert(ctx->doc); assert(DOC_RUBY_OBJECT_TEST(ctx->doc)); switch(xpath->type) { case XPATH_STRING: thing = NOKOGIRI_STR_NEW2(xpath->stringval); xmlFree(xpath->stringval); break; case XPATH_NODESET: thing = Nokogiri_wrap_xml_node_set(xpath->nodesetval, DOC_RUBY_OBJECT(ctx->doc)); break; case XPATH_NUMBER: thing = rb_float_new(xpath->floatval); break; case XPATH_BOOLEAN: thing = xpath->boolval == 1 ? Qtrue : Qfalse; break; default: thing = Nokogiri_wrap_xml_node_set(NULL, DOC_RUBY_OBJECT(ctx->doc)); } xmlXPathFreeNodeSetList(xpath); return thing; }
Evaluate the search_path
returning an XML::XPath
object.
# File lib/nokogiri/xml/xpath_context.rb, line 7 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.