Module: Handsoap::XmlQueryFront

Defined in:
lib/handsoap/xml_query_front.rb

Overview

A simple frontend for parsing XML document with Xpath.

This provides a unified interface for multiple xpath-capable dom-parsers, allowing seamless switching between the underlying implementations.

A document is loaded using the function Handsoap::XmlQueryFront.parse_string, passing the xml source string and a driver, which can (currently) be one of:

:rexml
:nokogiri
:libxml

The resulting object is a wrapper, of the type Handsoap::XmlQueryFront::XmlElement.

Defined Under Namespace

Modules: XmlElement Classes: LibXMLDriver, NodeSelection, NokogiriDriver, ParseError, REXMLDriver

Class Method Summary collapse

Class Method Details

.load_driver!(driver) ⇒ Object

Loads requirements for a driver.

This function is implicitly called by parse_string.



26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/handsoap/xml_query_front.rb', line 26

def self.load_driver!(driver)
  if driver == :rexml
    require 'rexml/document'
  elsif driver == :nokogiri
    require 'nokogiri'
    begin
      gem('nokogiri') # work around bug in rubygems for Ruby 1.9

      if Gem.loaded_specs['nokogiri'].version < Gem::Version.new('1.3.0')
        raise "Incompatible version of Nokogiri. Please upgrade gem."
      end
    rescue NoMethodError
    end
  elsif driver == :libxml
    require 'libxml'
  else
    raise "Unknown driver #{driver}"
  end
  return driver
end

.parse_string(xml_string, driver) ⇒ Object

Returns a wrapped XML parser, using the requested driver.

driver can be one of the following:

:rexml
:nokogiri
:libxml


53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/handsoap/xml_query_front.rb', line 53

def self.parse_string(xml_string, driver)
  load_driver!(driver)
  if driver == :rexml
    doc = REXML::Document.new(xml_string)
    raise ParseError.new if doc.root.nil?
    XmlQueryFront::REXMLDriver.new(doc)
  elsif driver == :nokogiri
    doc = Nokogiri::XML(xml_string)
    raise ParseError.new unless (doc && doc.root && doc.errors.empty?)
    XmlQueryFront::NokogiriDriver.new(doc)
  elsif driver == :libxml
    begin
      LibXML::XML::Error.set_handler &LibXML::XML::Error::QUIET_HANDLER
      doc = XmlQueryFront::LibXMLDriver.new(LibXML::XML::Parser.string(xml_string).parse)
    rescue ArgumentError, LibXML::XML::Error => ex
      raise ParseError.new
    end
  end
end