class AbrtProxy::HostReport

Attributes

by_hash[R]
files[R]
host[R]
reports[R]

Public Class Methods

load_from_spool() click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 200
def self.load_from_spool
  reports = []
  report_files = Dir[File.join(HostReport.spooldir, "ureport-*")]
  report_files.each do |fname|
    begin
      reports << new(fname)
    rescue => e
      logger.error "Failed to parse report #{fname}: #{e}"
    end
  end
  reports
end
new(fname) click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 128
def initialize(fname)
  contents = IO.read(fname)
  json = JSON.parse(contents)

  [:report, :reported_at, :host].each do |field|
    if !json.has_key?(field.to_s)
      raise AbrtProxy::Error::SyntaxError, "Report #{fname} missing field #{field}"
    end
  end

  report = json["report"]
  hash = HostReport.duphash report
  ar = AggregatedReport.new(json["report"], 1, hash, json["reported_at"])
  @reports = [ar]
  # index the array elements by duphash, if they have one
  @by_hash = {}
  @by_hash[hash] = ar unless hash.nil?
  @files = [fname]
  @host = json["host"]
  @althosts = json["althosts"]
end
save(hostnames, report, reported_at=nil) click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 181
def self.save(hostnames, report, reported_at=nil)
  # create the spool dir if it does not exist
  FileUtils.mkdir_p HostReport.spooldir

  reported_at ||= Time.now.utc
  on_disk_report = { "host" => hostnames[0], "report" => report , "reported_at" => reported_at.to_s, "althosts" => hostnames[1..-1] }

  # write report to temporary file
  temp_fname = unique_filename "new-"
  File.open temp_fname, File::WRONLY|File::CREAT|File::EXCL do |tmpfile|
    tmpfile.write(on_disk_report.to_json)
  end

  # rename it
  final_fname = unique_filename("ureport-" + DateTime.now.strftime("%FT%T") + "-")
  File.link temp_fname, final_fname
  File.unlink temp_fname
end

Private Class Methods

duphash(report) click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 236
def self.duphash(report)
  return nil if !AbrtProxy::Plugin.settings.aggregate_reports

  begin
    satyr_report = Satyr::Report.new report.to_json
    stacktrace = satyr_report.stacktrace
    thread = stacktrace.find_crash_thread
    thread.duphash
  rescue => e
    logger.error "Error computing duphash: #{e}"
    nil
  end
end
spooldir() click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 254
def self.spooldir
  AbrtProxy::Plugin.settings.spooldir
end
unique_filename(prefix) click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 250
def self.unique_filename(prefix)
  File.join(HostReport.spooldir, prefix + AbrtProxy::random_hex_string(8))
end

Public Instance Methods

merge(other) click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 150
def merge(other)
  raise HostReport::Error, "Host names do not match" unless @host == other.host

  other.reports.each do |ar|
    if !ar.hash.nil? && @by_hash.has_key?(ar.hash)
      # we already have this report, just increment the counter
      found_report = @by_hash[ar.hash]
      found_report.count += ar.count
      found_report.reported_at = [found_report.reported_at, ar.reported_at].min
    else
      # we either don't have this report or it has no hash
      @reports << ar
      @by_hash[ar.hash] = ar unless ar.hash.nil?
    end
  end
  @files += other.files
end
send_to_foreman() click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 168
def send_to_foreman
  foreman_report = create_foreman_report
  logger.debug "Sending #{foreman_report}"
  AbrtRequest.new.post_report(foreman_report.to_json)
end

Private Instance Methods

create_foreman_report() click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 227
def create_foreman_report
  { "abrt_report" => {
        "host"        => @host,
        "althosts"    => @althosts,
        "reports"     => format_reports
    }
  }
end
format_reports() click to toggle source
# File lib/smart_proxy_abrt/abrt_lib.rb, line 215
def format_reports
  @reports.collect do |ar|
    r = {
      "count"       => ar.count,
      "reported_at" => ar.reported_at.utc.to_s,
      "full"        => ar.report
    }
    r["duphash"] = ar.hash unless ar.hash.nil?
    r
  end
end