class Qualys::Element
This class represents each of the /SCAN/IP/[INFOS|SERVICES|VULNS|PRACTICES]/CAT/ elements in the Qualys
XML document.
It provides a convenient way to access the information scattered all over the XML in attributes and nested tags.
Instead of providing separate methods for each supported property we rely on Ruby's method_missing
to do most of the work.
Public Class Methods
new(xml_node)
click to toggle source
Accepts an XML node from Nokogiri::XML.
# File lib/qualys/element.rb, line 12 def initialize(xml_node) @xml = xml_node end
Public Instance Methods
method_missing(method, *args)
click to toggle source
This method is invoked by Ruby when a method that is not defined in this instance is called.
In our case we inspect the @method@ parameter and try to find the attribute, simple descendent or collection that it maps to in the XML tree.
Calls superclass method
# File lib/qualys/element.rb, line 45 def method_missing(method, *args) # We could remove this check and return nil for any non-recognized tag. # The problem would be that it would make tricky to debug problems with # typos. For instance: <>.potr would return nil instead of raising an # exception unless supported_tags.include?(method) super return end # First we try the attributes. In Ruby we use snake_case, but in XML # CamelCase is used for some attributes # translations_table = { # :nexpose_id => 'id', # :pci_severity => 'pciSeverity', # :cvss_score => 'cvssScore', # :cvss_vector =>'cvssVector' # } # # method_name = translations_table.fetch(method, method.to_s) method_name = method.to_s return @xml.attributes[method_name].value if @xml.attributes.key?(method_name) # Then we try simple children tags: TITLE, LAST_UPDATE, CVSS_BASE... tag = @xml.xpath("./#{method_name.upcase}").first if tag && !tag.text.blank? if tags_with_html_content.include?(method) return cleanup_html(tag.text) else return tag.text end else 'n/a' end # Finally the enumerations: vendor_reference_list, cve_id_list, bugtraq_id_list if method_name == 'references' # @xml.xpath("./references/reference").collect{|entry| {:source => entry['source'], :text => entry.text} } elsif method == 'tags' # @xml.xpath("./tags/tag").collect(&:text) else # nothing found, the tag is valid but not present in this ReportItem return nil end end
respond_to?(method, include_private=false)
click to toggle source
This allows external callers (and specs) to check for implemented properties
Calls superclass method
# File lib/qualys/element.rb, line 34 def respond_to?(method, include_private=false) return true if supported_tags.include?(method.to_sym) super end
Private Instance Methods
cleanup_html(source)
click to toggle source
# File lib/qualys/element.rb, line 93 def cleanup_html(source) result = source.dup result.gsub!(/"/, '"') result.gsub!(/</, '<') result.gsub!(/>/, '>') result.gsub!(/<p>/i, "\n\n") result.gsub!(/<br>/i, "\n") result.gsub!(/ /, "") result.gsub!(/<a href=\"(.*?)\" target=\"_blank\">(.*?)<\/a>/i) { "\"#{$2.strip}\":#{$1.strip}" } result.gsub!(/<pre>(.*?)<\/pre>/im) { |m| "\n\nbc.. #{$1.strip}\n\np. \n" } result.gsub!(/<b>(.*?)<\/b>/i) { "*#{$1.strip}*" } result.gsub!(/<i>(.*?)<\/i>/i) { "_#{$1.strip}_" } result end