Example #1
0
def associate_bug(report_id):
    result = (db.session.query(Report,
                               OpSysComponent).join(OpSysComponent).filter(
                                   Report.id == report_id).first())

    if result is None:
        abort(404)

    report, component = result

    is_maintainer = is_component_maintainer(db, g.user, component)

    if not is_maintainer:
        flash("You are not the maintainer of this component.", "danger")
        return redirect(url_for("reports.item", report_id=report_id))

    form = AssociateBzForm(request.form)
    if request.method == "POST" and form.validate():
        bug_id = form.bug_id.data

        reportbug = (db.session.query(
            ReportBz).filter((ReportBz.report_id == report.id)
                             & (ReportBz.bzbug_id == bug_id)).first())

        if reportbug:
            flash("Bug already associated.", "danger")
        else:
            bug = get_bz_bug(db, bug_id)
            if not bug:
                tracker = bugtrackers[form.bugtracker.data]

                try:
                    bug = tracker.download_bug_to_storage_no_retry(db, bug_id)
                except Exception as e:
                    flash("Failed to fetch bug. {0}".format(str(e)), "danger")
                    raise

            if bug:
                new = ReportBz()
                new.report = report
                new.bzbug = bug
                db.session.add(new)
                db.session.flush()
                db.session.commit()

                flash("Bug successfully associated.", "success")
                return redirect(url_for("reports.item", report_id=report_id))
            else:
                flash("Failed to fetch bug.", "danger")

    bthash_url = url_for("reports.bthash_forward",
                         bthash=report.hashes[0].hash,
                         _external=True)
    new_bug_params = {
        "component":
        component.name,
        "short_desc":
        "[abrt] [faf] {0}: {1}(): {2} killed by {3}".format(
            component.name, report.crash_function,
            ",".join(exe.path for exe in report.executables), report.errname),
        "comment":
        "This bug has been created based on an anonymous crash "
        "report requested by the package maintainer.\n\n"
        "Report URL: {0}".format(bthash_url),
        "bug_file_loc":
        bthash_url
    }

    new_bug_urls = []
    for rosr in report.opsysreleases:
        osr = rosr.opsysrelease
        for bugtracker in bugtrackers.keys():
            try:
                params = new_bug_params.copy()
                if osr.opsys.name.startswith("Red Hat"):
                    params.update(product="{0} {1}".format(
                        osr.opsys.name, osr.version[0]),
                                  version=osr.version)
                else:
                    params.update(product=osr.opsys.name, version=osr.version)
                print(params)
                new_bug_urls.append(
                    ("{0} {1} in {2}".format(osr.opsys.name, osr.version,
                                             bugtracker),
                     "{0}?{1}".format(bugtrackers[bugtracker].new_bug_url,
                                      urllib.urlencode(params))))
            except:
                pass

    return render_template("reports/associate_bug.html",
                           form=form,
                           report=report,
                           new_bug_urls=new_bug_urls)
Example #2
0
def item(report_id):
    result = (db.session.query(Report,
                               OpSysComponent).join(OpSysComponent).filter(
                                   Report.id == report_id).first())

    if result is None:
        abort(404)

    report, component = result

    releases = (db.session.query(
        ReportOpSysRelease, ReportOpSysRelease.count).filter(
            ReportOpSysRelease.report_id == report_id).order_by(
                desc(ReportOpSysRelease.count)).all())

    arches = (db.session.query(
        ReportArch,
        ReportArch.count).filter(ReportArch.report_id == report_id).order_by(
            desc(ReportArch.count)).all())

    modes = (db.session.query(
        ReportSelinuxMode, ReportSelinuxMode.count).filter(
            ReportSelinuxMode.report_id == report_id).order_by(
                desc(ReportSelinuxMode.count)).all())

    history_select = lambda table, date: (
        db.session.query(table).filter(table.report_id == report_id)
        # Flot is confused if not ordered
        .order_by(date).all())

    daily_history = history_select(ReportHistoryDaily, ReportHistoryDaily.day)
    weekly_history = history_select(ReportHistoryWeekly,
                                    ReportHistoryWeekly.week)
    monthly_history = history_select(ReportHistoryMonthly,
                                     ReportHistoryMonthly.month)

    packages = load_packages(db, report_id)

    # creates a package_counts list with this structure:
    # [(package name, count, [(package version, count in the version)])]
    names = defaultdict(lambda: {"count": 0, "versions": defaultdict(int)})
    for pkg in packages:
        names[pkg.iname]["name"] = pkg.iname
        names[pkg.iname]["count"] += pkg.count
        names[pkg.iname]["versions"]["{0}:{1}-{2}".format(
            pkg.iepoch, pkg.iversion, pkg.irelease)] += pkg.count

    package_counts = []
    for pkg in sorted(names.values(), key=itemgetter("count"), reverse=True):
        package_counts.append((pkg["name"], pkg["count"],
                               sorted(pkg["versions"].items(),
                                      key=itemgetter(1),
                                      reverse=True)))

    try:
        backtrace = report.backtraces[0].frames
    except:
        backtrace = []

    fid = 0
    for frame in backtrace:
        fid += 1
        frame.nice_order = fid

    is_maintainer = is_component_maintainer(db, g.user, component)

    contact_emails = []
    if is_maintainer:
        contact_emails = [
            email_address for (email_address, ) in (db.session.query(
                ContactEmail.email_address).join(ReportContactEmail).filter(
                    ReportContactEmail.report == report))
        ]

    forward = dict(report=report,
                   component=component,
                   releases=metric(releases),
                   arches=metric(arches),
                   modes=metric(modes),
                   daily_history=daily_history,
                   weekly_history=weekly_history,
                   monthly_history=monthly_history,
                   crashed_packages=packages,
                   package_counts=package_counts,
                   backtrace=backtrace,
                   contact_emails=contact_emails)

    if request_wants_json():
        return jsonify(forward)

    forward["is_maintainer"] = is_maintainer
    forward["extfafs"] = get_external_faf_instances(db)
    return render_template("reports/item.html", **forward)
Example #3
0
File: reports.py Project: sorki/faf
def associate_bug(report_id):
    result = (db.session.query(Report, OpSysComponent)
              .join(OpSysComponent)
              .filter(Report.id == report_id)
              .first())

    if result is None:
        abort(404)

    report, component = result

    is_maintainer = is_component_maintainer(db, g.user, component)

    if not is_maintainer:
        flash("You are not the maintainer of this component.", "danger")
        return redirect(url_for("reports.item", report_id=report_id))

    form = AssociateBzForm(request.form)
    if request.method == "POST" and form.validate():
        bug_id = form.bug_id.data

        reportbug = (db.session.query(ReportBz)
                     .filter(
                         (ReportBz.report_id == report.id) &
                         (ReportBz.bzbug_id == bug_id))
                     .first())

        if reportbug:
            flash("Bug already associated.", "danger")
        else:
            bug = get_bz_bug(db, bug_id)
            if not bug:
                tracker = bugtrackers[form.bugtracker.data]

                try:
                    bug = tracker.download_bug_to_storage_no_retry(db, bug_id)
                except Exception as e:
                    flash("Failed to fetch bug. {0}".format(str(e)), "danger")
                    raise

            if bug:
                new = ReportBz()
                new.report = report
                new.bzbug = bug
                db.session.add(new)
                db.session.flush()
                db.session.commit()

                flash("Bug successfully associated.", "success")
                return redirect(url_for("reports.item", report_id=report_id))
            else:
                flash("Failed to fetch bug.", "danger")

    bthash_url = url_for("reports.bthash_forward",
                         bthash=report.hashes[0].hash,
                         _external=True)
    new_bug_params = {
        "component": component.name,
        "short_desc": "[abrt] [faf] {0}: {1}(): {2} killed by {3}"
                      .format(component.name,
                              report.crash_function,
                              ",".join(exe.path for exe in report.executables),
                              report.errname
                              ),
        "comment": "This bug has been created based on an anonymous crash "
                   "report requested by the package maintainer.\n\n"
                   "Report URL: {0}"
                   .format(bthash_url),
        "bug_file_loc": bthash_url
    }

    new_bug_urls = []
    for rosr in report.opsysreleases:
        osr = rosr.opsysrelease
        for bugtracker in bugtrackers.keys():
            try:
                params = new_bug_params.copy()
                if osr.opsys.name.startswith("Red Hat"):
                    params.update(product="{0} {1}".format(osr.opsys.name,
                                                           osr.version[0]),
                                  version=osr.version)
                else:
                    params.update(product=osr.opsys.name, version=osr.version)
                print(params)
                new_bug_urls.append(
                    ("{0} {1} in {2}".format(osr.opsys.name, osr.version,
                                             bugtracker),
                     "{0}?{1}".format(
                        bugtrackers[bugtracker].new_bug_url,
                        urllib.urlencode(params))
                     )
                )
            except:
                pass

    return render_template("reports/associate_bug.html",
                           form=form,
                           report=report,
                           new_bug_urls=new_bug_urls)
Example #4
0
File: reports.py Project: sorki/faf
def item(report_id):
    result = (db.session.query(Report, OpSysComponent)
              .join(OpSysComponent)
              .filter(Report.id == report_id)
              .first())

    if result is None:
        abort(404)

    report, component = result

    releases = (db.session.query(ReportOpSysRelease, ReportOpSysRelease.count)
                .filter(ReportOpSysRelease.report_id == report_id)
                .order_by(desc(ReportOpSysRelease.count))
                .all())

    arches = (db.session.query(ReportArch, ReportArch.count)
              .filter(ReportArch.report_id == report_id)
              .order_by(desc(ReportArch.count))
              .all())

    modes = (db.session.query(ReportSelinuxMode, ReportSelinuxMode.count)
             .filter(ReportSelinuxMode.report_id == report_id)
             .order_by(desc(ReportSelinuxMode.count))
             .all())

    history_select = lambda table, date: (db.session.query(table).
                                          filter(table.report_id == report_id)
                                          # Flot is confused if not ordered
                                          .order_by(date)
                                          .all())

    daily_history = history_select(ReportHistoryDaily, ReportHistoryDaily.day)
    weekly_history = history_select(ReportHistoryWeekly, ReportHistoryWeekly.week)
    monthly_history = history_select(ReportHistoryMonthly, ReportHistoryMonthly.month)

    packages = load_packages(db, report_id)

    # creates a package_counts list with this structure:
    # [(package name, count, [(package version, count in the version)])]
    names = defaultdict(lambda: {"count": 0, "versions": defaultdict(int)})
    for pkg in packages:
        names[pkg.iname]["name"] = pkg.iname
        names[pkg.iname]["count"] += pkg.count
        names[pkg.iname]["versions"]["{0}:{1}-{2}"
            .format(pkg.iepoch, pkg.iversion, pkg.irelease)] += pkg.count

    package_counts = []
    for pkg in sorted(names.values(), key=itemgetter("count"), reverse=True):
        package_counts.append((
            pkg["name"],
            pkg["count"],
            sorted(pkg["versions"].items(), key=itemgetter(1), reverse=True)))

    try:
        backtrace = report.backtraces[0].frames
    except:
        backtrace = []

    fid = 0
    for frame in backtrace:
        fid += 1
        frame.nice_order = fid

    is_maintainer = is_component_maintainer(db, g.user, component)

    contact_emails = []
    if is_maintainer:
        contact_emails = [email_address for (email_address, ) in
                          (db.session.query(ContactEmail.email_address)
                                     .join(ReportContactEmail)
                                     .filter(ReportContactEmail.report == report))]

    forward = dict(report=report,
                   component=component,
                   releases=metric(releases),
                   arches=metric(arches),
                   modes=metric(modes),
                   daily_history=daily_history,
                   weekly_history=weekly_history,
                   monthly_history=monthly_history,
                   crashed_packages=packages,
                   package_counts=package_counts,
                   backtrace=backtrace,
                   contact_emails=contact_emails)

    if request_wants_json():
        return jsonify(forward)

    forward["is_maintainer"] = is_maintainer
    forward["extfafs"] = get_external_faf_instances(db)
    return render_template("reports/item.html", **forward)
Example #5
0
def item(report_id, want_object=False):
    result = (db.session.query(Report,
                               OpSysComponent).join(OpSysComponent).filter(
                                   Report.id == report_id).first())

    if result is None:
        abort(404)

    report, component = result

    executable = (db.session.query(ReportExecutable.path).filter(
        ReportExecutable.report_id == report_id).scalar())

    solutions = None

    if report.max_certainty is not None:
        osr = get_report_opsysrelease(db=db, report_id=report.id)
        solutions = [find_solution(report, db=db, osr=osr)]

    releases = (db.session.query(
        ReportOpSysRelease, ReportOpSysRelease.count).filter(
            ReportOpSysRelease.report_id == report_id).order_by(
                desc(ReportOpSysRelease.count)).all())

    arches = (db.session.query(
        ReportArch,
        ReportArch.count).filter(ReportArch.report_id == report_id).order_by(
            desc(ReportArch.count)).all())

    modes = (db.session.query(
        ReportSelinuxMode, ReportSelinuxMode.count).filter(
            ReportSelinuxMode.report_id == report_id).order_by(
                desc(ReportSelinuxMode.count)).all())

    history_select = lambda table, date, date_range: (
        db.session.query(table).filter(table.report_id == report_id).filter(
            date >= date_range)
        # Flot is confused if not ordered
        .order_by(date).all())

    MAX_DAYS = 20  # Default set on 20
    MAX_WEEK = 20  # Default set on 20
    MAX_MONTH = 20  # Default set on 20

    today = datetime.date.today()

    # Show only 20 days
    daily_history = history_select(ReportHistoryDaily, ReportHistoryDaily.day,
                                   (today - timedelta(days=MAX_DAYS)))

    if len(daily_history) == 0:
        for x in range(0, MAX_DAYS):
            daily_history.append({
                'day':
                today - timedelta(x),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

    elif len(daily_history) < MAX_DAYS:
        if daily_history[-1].day < (today):
            daily_history.append({
                'day':
                today,
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

        if daily_history[0].day > (today - timedelta(MAX_DAYS)):
            daily_history.append({
                'day':
                today - timedelta(MAX_DAYS),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

    # Show only 20 weeks
    last_monday = datetime.datetime.today() - timedelta(
        datetime.datetime.today().weekday())

    weekly_history = history_select(
        ReportHistoryWeekly, ReportHistoryWeekly.week,
        (last_monday - timedelta(days=MAX_WEEK * 7)))
    if len(weekly_history) == 0:
        for x in range(0, MAX_WEEK):
            weekly_history.append({
                'week':
                last_monday - timedelta(x * 7),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })
    elif len(weekly_history) < MAX_WEEK:
        if weekly_history[-1].week < (last_monday.date()):
            weekly_history.append({
                'week':
                last_monday,
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

        if weekly_history[0].week > (
            (last_monday - timedelta(7 * MAX_WEEK)).date()):
            weekly_history.append({
                'week':
                last_monday - timedelta(7 * MAX_WEEK),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

    # Show only 20 months
    monthly_history = history_select(ReportHistoryMonthly,
                                     ReportHistoryMonthly.month,
                                     (today - relativedelta(months=MAX_MONTH)))

    first_day_of_month = lambda t: (datetime.date(t.year, t.month, 1))

    fdom = first_day_of_month(datetime.datetime.today())

    if len(monthly_history) == 0:
        for x in range(0, MAX_MONTH):
            monthly_history.append({
                'month':
                fdom - relativedelta(months=x),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

    elif len(monthly_history) < MAX_MONTH:
        if monthly_history[-1].month < (fdom):
            monthly_history.append({
                'month':
                fdom,
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

        if monthly_history[0].month > (fdom - relativedelta(months=MAX_MONTH)):
            monthly_history.append({
                'month':
                fdom - relativedelta(months=MAX_MONTH),
                'count':
                0,
                'opsysrelease_id':
                releases[0].ReportOpSysRelease.opsysrelease_id
            })

    complete_history = history_select(
        ReportHistoryMonthly, ReportHistoryMonthly.month,
        (datetime.datetime.strptime('1970-01-01', '%Y-%m-%d')))

    unique_ocurrence_os = {}
    if len(complete_history) > 0:
        for ch in complete_history:
            os_name = "{0} {1}".format(ch.opsysrelease.opsys.name,
                                       ch.opsysrelease.version)

            if ch.count is None:
                ch.count = 0

            if ch.unique is None:
                ch.count = 0

            if os_name not in unique_ocurrence_os:
                unique_ocurrence_os[os_name] = {
                    'count': ch.count,
                    'unique': ch.unique
                }
            else:
                unique_ocurrence_os[os_name]['count'] += ch.count
                unique_ocurrence_os[os_name]['unique'] += ch.unique

    sorted(unique_ocurrence_os)

    packages = load_packages(db, report_id)

    # creates a package_counts list with this structure:
    # [(package name, count, [(package version, count in the version)])]
    names = defaultdict(lambda: {"count": 0, "versions": defaultdict(int)})
    for pkg in packages:
        names[pkg.iname]["name"] = pkg.iname
        names[pkg.iname]["count"] += pkg.count
        names[pkg.iname]["versions"]["{0}:{1}-{2}".format(
            pkg.iepoch, pkg.iversion, pkg.irelease)] += pkg.count

    package_counts = []
    for pkg in sorted(names.values(), key=itemgetter("count"), reverse=True):
        package_counts.append((pkg["name"], pkg["count"],
                               sorted(pkg["versions"].items(),
                                      key=itemgetter(1),
                                      reverse=True)))

    try:
        backtrace = report.backtraces[0].frames
    except:
        backtrace = []

    fid = 0
    for frame in backtrace:
        fid += 1
        frame.nice_order = fid

    is_maintainer = is_component_maintainer(db, g.user, component)

    contact_emails = []
    if is_maintainer:
        contact_emails = [
            email_address for (email_address, ) in (db.session.query(
                ContactEmail.email_address).join(ReportContactEmail).filter(
                    ReportContactEmail.report == report))
        ]

    maintainer = (
        db.session.query(AssociatePeople).join(OpSysReleaseComponentAssociate).
        join(OpSysReleaseComponent).join(OpSysComponent).filter(
            OpSysComponent.name == component.name)).first()

    maintainer_contact = ""
    if maintainer:
        maintainer_contact = maintainer.name

    probably_fixed = (db.session.query(
        ProblemOpSysRelease,
        Build).join(Problem).join(Report).join(Build).filter(
            Report.id == report_id).first())

    forward = dict(report=report,
                   executable=executable,
                   probably_fixed=probably_fixed,
                   component=component,
                   releases=metric(releases),
                   arches=metric(arches),
                   modes=metric(modes),
                   daily_history=daily_history,
                   weekly_history=weekly_history,
                   monthly_history=monthly_history,
                   complete_history=complete_history,
                   unique_ocurrence_os=unique_ocurrence_os,
                   crashed_packages=packages,
                   package_counts=package_counts,
                   backtrace=backtrace,
                   contact_emails=contact_emails,
                   solutions=solutions,
                   maintainer_contact=maintainer_contact)

    forward['error_name'] = report.error_name
    forward['oops'] = report.oops

    if want_object:
        try:
            cf = component.name
            if len(report.backtraces[0].crash_function) > 0:
                cf += " in {0}".format(report.backtraces[0].crash_function)
            forward['crash_function'] = cf
        except:
            forward['crash_function'] = ""

        if probably_fixed:
            tmp_dict = probably_fixed.ProblemOpSysRelease.serialize
            tmp_dict['probable_fix_build'] = probably_fixed.Build.serialize

            forward['probably_fixed'] = tmp_dict
        # Avg count occurrence from first to last occurence
        forward['avg_count_per_month'] = get_avg_count(report.first_occurrence,
                                                       report.last_occurrence,
                                                       report.count)

        if len(forward['report'].bugs) > 0:
            forward['bugs'] = []
            for bug in forward['report'].bugs:
                try:
                    forward['bugs'].append(bug.serialize)
                except:
                    print "Bug serialize failed"
        return forward

    if request_wants_json():
        return jsonify(forward)

    forward["is_maintainer"] = is_maintainer
    forward["extfafs"] = get_external_faf_instances(db)

    return render_template("reports/item.html", **forward)
Example #6
0
def item(report_id, want_object=False):
    result = (db.session.query(Report, OpSysComponent)
              .join(OpSysComponent)
              .filter(Report.id == report_id)
              .first())

    if result is None:
        abort(404)

    report, component = result

    solutions = None

    if report.max_certainty is not None:
        osr = get_report_opsysrelease(db=db, report_id=report.id)
        solutions = [find_solution(report, db=db, osr=osr)]

    releases = (db.session.query(ReportOpSysRelease, ReportOpSysRelease.count)
                .filter(ReportOpSysRelease.report_id == report_id)
                .order_by(desc(ReportOpSysRelease.count))
                .all())

    arches = (db.session.query(ReportArch, ReportArch.count)
              .filter(ReportArch.report_id == report_id)
              .order_by(desc(ReportArch.count))
              .all())

    modes = (db.session.query(ReportSelinuxMode, ReportSelinuxMode.count)
             .filter(ReportSelinuxMode.report_id == report_id)
             .order_by(desc(ReportSelinuxMode.count))
             .all())

    history_select = lambda table, date, date_range: (db.session.query(table).
                                                      filter(table.report_id == report_id)
                                                      .filter(date >= date_range)
                                                      # Flot is confused if not ordered
                                                      .order_by(date)
                                                      .all())

    MAX_DAYS = 20  # Default set on 20
    MAX_WEEK = 20  # Default set on 20
    MAX_MONTH = 20  # Default set on 20

    today = datetime.date.today()

    # Show only 20 days
    daily_history = history_select(ReportHistoryDaily, ReportHistoryDaily.day,
                                   (today - timedelta(days=MAX_DAYS)))

    if len(daily_history) == 0:
        for x in range(0, MAX_DAYS):
            daily_history.append({'day': today - timedelta(x),
                                  'count': 0,
                                  'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

    elif len(daily_history) < MAX_DAYS:
        if daily_history[-1].day < (today):
            daily_history.append({'day': today,
                                  'count': 0,
                                  'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id
                                  })

        if daily_history[0].day > (today - timedelta(MAX_DAYS)):
            daily_history.append({'day': today - timedelta(MAX_DAYS),
                                  'count': 0,
                                  'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id
                                  })

    # Show only 20 weeks
    last_monday = datetime.datetime.today() - timedelta(datetime.datetime.today().weekday())

    weekly_history = history_select(ReportHistoryWeekly, ReportHistoryWeekly.week,
                                    (last_monday - timedelta(days=MAX_WEEK*7)))
    if len(weekly_history) == 0:
        for x in range(0, MAX_WEEK):
            weekly_history.append({'week': last_monday - timedelta(x*7),
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})
    elif len(weekly_history) < MAX_WEEK:
        if weekly_history[-1].week < (last_monday.date()):
            weekly_history.append({'week': last_monday,
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

        if weekly_history[0].week > ((last_monday - timedelta(7*MAX_WEEK)).date()):
            weekly_history.append({'week': last_monday - timedelta(7*MAX_WEEK),
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

    # Show only 20 months
    monthly_history = history_select(ReportHistoryMonthly, ReportHistoryMonthly.month,
                                     (today - relativedelta(months=MAX_MONTH)))

    first_day_of_month = lambda t: (datetime.date(t.year, t.month, 1))

    fdom = first_day_of_month(datetime.datetime.today())

    if len(monthly_history) == 0:
        for x in range(0, MAX_MONTH):
            monthly_history.append({'month': fdom - relativedelta(months=x),
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

    elif len(monthly_history) < MAX_MONTH:
        if monthly_history[-1].month < (fdom):
            monthly_history.append({'month': fdom,
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

        if monthly_history[0].month > (fdom - relativedelta(months=MAX_MONTH)):
            monthly_history.append({'month': fdom - relativedelta(months=MAX_MONTH),
                                   'count': 0,
                                   'opsysrelease_id': releases[0].ReportOpSysRelease.opsysrelease_id})

    complete_history = history_select(ReportHistoryMonthly, ReportHistoryMonthly.month,
                                    (datetime.datetime.strptime('1970-01-01', '%Y-%m-%d')))

    unique_ocurrence_os = {}
    if len(complete_history) > 0:
        for ch in complete_history:
            os_name = "{0} {1}".format(ch.opsysrelease.opsys.name, ch.opsysrelease.version)

            if ch.count is None:
                ch.count = 0

            if ch.unique is None:
                ch.count = 0

            if os_name not in unique_ocurrence_os:
                unique_ocurrence_os[os_name] = {'count': ch.count, 'unique': ch.unique}
            else:
                unique_ocurrence_os[os_name]['count'] += ch.count
                unique_ocurrence_os[os_name]['unique'] += ch.unique

    sorted(unique_ocurrence_os)

    packages = load_packages(db, report_id)

    # creates a package_counts list with this structure:
    # [(package name, count, [(package version, count in the version)])]
    names = defaultdict(lambda: {"count": 0, "versions": defaultdict(int)})
    for pkg in packages:
        names[pkg.iname]["name"] = pkg.iname
        names[pkg.iname]["count"] += pkg.count
        names[pkg.iname]["versions"]["{0}:{1}-{2}"
            .format(pkg.iepoch, pkg.iversion, pkg.irelease)] += pkg.count

    package_counts = []
    for pkg in sorted(names.values(), key=itemgetter("count"), reverse=True):
        package_counts.append((
            pkg["name"],
            pkg["count"],
            sorted(pkg["versions"].items(), key=itemgetter(1), reverse=True)))

    try:
        backtrace = report.backtraces[0].frames
    except:
        backtrace = []

    fid = 0
    for frame in backtrace:
        fid += 1
        frame.nice_order = fid

    is_maintainer = is_component_maintainer(db, g.user, component)

    contact_emails = []
    if is_maintainer:
        contact_emails = [email_address for (email_address, ) in
                          (db.session.query(ContactEmail.email_address)
                                .join(ReportContactEmail)
                                .filter(ReportContactEmail.report == report))]

    maintainer = (db.session.query(AssociatePeople)
                        .join(OpSysReleaseComponentAssociate)
                        .join(OpSysReleaseComponent)
                        .join(OpSysComponent)
                        .filter(OpSysComponent.name == component.name)).first()

    maintainer_contact = ""
    if maintainer:
        maintainer_contact = maintainer.name

    probably_fixed = (db.session.query(ProblemOpSysRelease, Build)
                      .join(Problem)
                      .join(Report)
                      .join(Build)
                      .filter(Report.id == report_id)
                      .first())

    forward = dict(report=report,
                   probably_fixed=probably_fixed,
                   component=component,
                   releases=metric(releases),
                   arches=metric(arches),
                   modes=metric(modes),
                   daily_history=daily_history,
                   weekly_history=weekly_history,
                   monthly_history=monthly_history,
                   complete_history=complete_history,
                   unique_ocurrence_os=unique_ocurrence_os,
                   crashed_packages=packages,
                   package_counts=package_counts,
                   backtrace=backtrace,
                   contact_emails=contact_emails,
                   solutions=solutions,
                   maintainer_contact=maintainer_contact)

    forward['error_name'] = report.error_name
    forward['oops'] = report.oops

    if want_object:
        try:
            cf = component.name
            if len(report.backtraces[0].crash_function) > 0:
                cf += " in {0}".format(report.backtraces[0].crash_function)
            forward['crash_function'] = cf
        except:
            forward['crash_function'] = ""

        if probably_fixed:
            tmp_dict = probably_fixed.ProblemOpSysRelease.serialize
            tmp_dict['probable_fix_build'] = probably_fixed.Build.serialize

            forward['probably_fixed'] = tmp_dict
        # Avg count occurrence from first to last occurence
        forward['avg_count_per_month'] = get_avg_count(report.first_occurrence,
                                                           report.last_occurrence,
                                                           report.count)

        if len(forward['report'].bugs) > 0:
            forward['bugs'] = []
            for bug in forward['report'].bugs:
                try:
                    forward['bugs'].append(bug.serialize)
                except:
                    print "Bug serialize failed"
        return forward

    if request_wants_json():
        return jsonify(forward)

    forward["is_maintainer"] = is_maintainer
    forward["extfafs"] = get_external_faf_instances(db)

    return render_template("reports/item.html", **forward)