summaryrefslogtreecommitdiff
blob: 9da61a23340934ab6234389e41fdaeade404debe (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
require 'date'

# A version 1 GLSA
class GLSAv1
  attr_reader :id, :title, :synopsis, :product, :date, :revised, :revision, :bugs, :access, :packages,
              :background, :description, :severity, :impact, :workaround, :resolution, :references

  def parse(xml)
    @id          = xml.root['id']
    @title       = text_content xml, '/glsa/title/text()'
    @synopsis    = text_content xml, '/glsa/synopsis/text()'
    @product     = text_content xml, '/glsa/product/text()'
    @date        = DateTime.parse(xml.xpath('/glsa/announced/text()').first.content)

    if xml.xpath('/glsa/revised').first['count'].nil?
      @revised,
      @revision  = xml.xpath('/glsa/revised/text()').first.content.split(': ')
    else
      @revised   = xml.xpath('/glsa/revised/text()').first.content
      @revision  = xml.xpath('/glsa/revised').first['count']
    end
    @revised     = DateTime.parse(@revised)

    @bugs        = xml.xpath('/glsa/bug/text()').map { |bug_node| bug_node.content.to_i }
    @access      = xml.xpath('/glsa/access/text()').first.content

    @packages    = {}
    xml.xpath('/glsa/affected/package').each do |package|
      @packages[package['name'] + ':' + package['arch']] = {
        auto:       package['auto'] == 'yes',
        unaffected: package.xpath('./unaffected').map { |ver| [ver['range'], ver.content] },
        vulnerable: package.xpath('./vulnerable').map { |ver| [ver['range'], ver.content] }
      }
    end

    @background  = xml_content xml, '/glsa/background'
    @description = xml_content xml, '/glsa/description'
    @severity    = xml.xpath('/glsa/impact').first['type']
    @impact      = xml_content xml, '/glsa/impact'
    @workaround  = xml_content xml, '/glsa/workaround'
    @resolution  = xml_content xml, '/glsa/resolution'
    @references  = xml.xpath('/glsa/references/uri').map { |uri| [uri.content, uri['link']] }

    self
  end

  private

  def xml_content(xml, xpath)
    xml.xpath(xpath).first.children.to_xml.strip
  rescue
    ''
  end

  def text_content(xml, xpath)
    xml.xpath(xpath).first.content
  rescue
    ''
  end
end