Skip to content

Add the gecko-triage agent for Gecko bug triage - #7239

Open
alastor0325 wants to merge 3 commits into
mozilla:masterfrom
alastor0325:gecko-triage/pr
Open

alastor0325 wants to merge 3 commits into
mozilla:masterfrom
alastor0325:gecko-triage/pr

Conversation

@alastor0325

Copy link
Copy Markdown
Member

Background

The Firefox media team triages its new bugs with the /triage skill of fx-bug-toolkit. fx-bug-toolkit is a Claude Code plugin. The media team has used this skill for weekly triage for a while.

For each bug, the skill does these steps:

  • It reads the bug and finds the data that is missing.
  • It looks for duplicates.
  • It reads the attached profiles and logs.
  • It writes a draft comment and the field changes.

This PR brings that workflow into Hackbot as the gecko-triage agent. The agent does not call /triage. Its own rules (rules/ and teams/<team>/rules/) and its code now hold the triage steps. The agent still uses four helper skills of fx-bug-toolkit, at version 0.7.0, in their Hackbot mode:

  • analyze-profile reads Firefox Profiler links.
  • check-log reads media logs.
  • spec-check checks web spec behavior.
  • bug-start investigates the cause in the code.

The agent records its comment and its field changes as actions.

We've been runing the agent in this PR locally every day in the past week o media bugs, and a person reviewed each result before it was posted to refine the PR to current shape. The gecko-triage dashboard shows these results.

One agent can triage for each Gecko team. A team adds its components and its rules in teams/<team>/. The media team is the first team. A run with no team uses only the shared rules, in the component of the bug.

Architecture

Each box names its main file. The table below lists all the files for each box. The agent's files are in agents/gecko-triage/hackbot_agents/gecko_triage/.

flowchart LR
    ui[Hackbot UI or API<br/>bug_id, team]
    api[hackbot-api<br/>app/agents.py]
    subgraph job[Cloud Run job]
        direction TB
        pre[Preflight<br/>preflight.py]
        agent[gecko-triage agent<br/>agent.py]
        subs[Subagents<br/>agent.py, dupes.py, toolkit.py]
        hooks[Record-time hooks<br/>hooks.py, closing.py]
        post[Post-run checks<br/>targets.py]
        broker[Broker sidecar<br/>broker.py]
        pre --> agent
        agent --> subs
        agent -- comment and field changes --> hooks
        hooks --> post
        agent -. reads .-> broker
        subs -. reads .-> broker
    end
    bmo[(Bugzilla)]
    person{{A person approves<br/>in the Hackbot UI}}
    ui --> api --> job
    broker -. read-only key .-> bmo
    post -- recorded actions --> api
    api --> person -- apply --> bmo
Loading
Box Files What it does
hackbot-api services/hackbot-api/app/agents.py, app/schemas.py Registers the agent with auto_apply_actions=False, and checks the run inputs bug_id and team.
Preflight preflight.py, state.py Reads the bug and stops the run before the model starts when the rules say to leave the bug alone.
gecko-triage agent __main__.py, agent.py, rules/, teams/<team>/, config.py, teamconfig.py Runs the model with the triage rules, and checks the final result.
Subagents agent.py (the make_* functions), dupes.py, toolkit.py, attachments.py Read profiles, logs, specs, code and attachments, search for duplicates, and verify a close. toolkit.py loads the pinned fx-bug-toolkit skills.
Record-time hooks hooks.py, closing.py, authors.py Refuse a write that breaks a rule, at the moment the agent records it.
Post-run checks targets.py After the session, read the other bugs that a write or the comment names, and drop or hold a write that is not safe.
Broker sidecar broker.py, visibility.py Holds the Bugzilla key, and serves only public bugs, comments and attachments.
  • Reads. The agent holds no Bugzilla key. The broker sidecar holds it. The broker drops restricted bugs, private comments and private attachments.
  • Writes. The agent records one comment and the field changes that its rules allow. The record-time hooks refuse a write that breaks a rule. Examples are S1, P4 or P5, a needinfo on a person who is not on the bug or on the team's expert list, and a close with no check. The post-run checks then read the bugs that a write names.
  • Approval. Nothing reaches Bugzilla until a person approves the run in the Hackbot UI. hackbot-api registers gecko-triage with auto_apply_actions=False.
  • Closes. Every close (INVALID, DUPLICATE, INCOMPLETE) needs a confirm from close_verifier. This subagent starts with a fresh context, uses only read tools, and tries to prove the close wrong.
  • Model access. On Hackbot, the agent uses Workload Identity Federation. It needs no API key.
  • Starting runs. This PR adds no automatic trigger. A person starts a run from the Hackbot UI or API. A BugBot rule for daily runs is a separate change.

Workflow

Each run triages one bug. rules/workflow.md gives the steps.

  1. Preflight. Code, not the model, does this step. The run stops at no model cost when one of these is true:
    • The bug is restricted.
    • The bug is not in the team's components.
    • The bug is a meta bug.
    • The bug is closed.
    • A developer filed the bug and set its severity.
    • The agent wrote the newest comment, and nothing changed after it.
  2. Fetch. The agent reads the full bug: all the comments, the attachments and the open needinfos.
  3. Inventory. The agent records the data that the bug has. Subagents read the diagnostics with fx-bug-toolkit skills:
    • profile_analyst reads Firefox Profiler links.
    • log_analyst reads media logs.
    • spec_checker checks web spec behavior.
    • bug_investigator reads the code.
  4. Classify. The agent gives the bug its type and its main symptom (issue_type).
  5. Duplicates and meta bugs. duplicate_hunter searches for duplicates. Code runs some of the searches, and the subagent runs a concept search. The agent then links the correct meta bug.
  6. Gaps. The agent compares the data on the bug with the data that the bug type needs.
  7. Branch. The agent selects the decision. It records one comment and the field changes. Before a close, close_verifier must confirm the close.

Decisions

Decision What the run records
needs_info A comment that asks for the missing data, and a needinfo on the person who can give it. Severity and priority too.
analyzed The cause or a fix direction. The comment asks for no data. Severity, priority, meta bugs and the regression fields.
duplicate RESOLVED DUPLICATE, after close_verifier confirms it.
invalid RESOLVED INVALID (or WONTFIX), after close_verifier confirms it. Never when the reported input can cause a failure.
incomplete RESOLVED INCOMPLETE, after close_verifier confirms it. The reporter did not answer a needinfo for 14 days.
wrong_component A move to the component that owns the code, and a needinfo on a developer of that team.
stalled The stalled keyword. The a cause. The bug stays open.
watching Nothing. Nothing new occurred since the last request.
skipped Nothing. The preflight stopp decision, not the model.

@alastor0325
alastor0325 requested a review from a team as a code owner October 19, 2026 22:24

@suhaibmujahid suhaibmujahid left a comment •

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had a quick, relatively to the PR size ;) and I have some generic comments.

@padenot will take a look as well.

Comment thread .github/CODEOWNERS Resolved
Comment thread agents/gecko-triage/docs/bugzilla.md Resolved
Comment thread agents/cloudbuild.yaml Resolved
@alastor0325

Copy link
Copy Markdown
Member Author

I submitted another PR to start intergrating some of my skills into firefox-aidev-plugins, so we will eventually remove my own fx-bug-toolkit repo reference.

An agent's hooks need COMMENT_FOOTER_SEPARATOR to tell the agent's prose from the
runtime's trailer. A broker that wraps the agent-tools Bugzilla tools needs
GET_BUGS_DEFAULT_FIELDS to request the same default fields.
gecko-triage triages one Gecko bug per run, for one team or, with no team, with the
shared rules only. Each run reads the whole bug, all comments included, and decides its
status, what is missing and the next step. It reads the diagnostics reporters attach
(profiles, logs, CI logs, crash reports, archives, memory reports and video frames,
plus specs) through fx-bug-toolkit skills and its own tools, and it looks at the code
before it asks a reporter for more. It records one comment and the field changes its
rules allow. Record-time hooks limit every write, a post-run check reads the bugs a
write names, and a broker sidecar serves only public Bugzilla content. An independent,
read-only verifier must confirm every close before the hooks accept it. A run with no
team never applies by itself. The media team is the first team.
The agent starts human-gated: auto_apply_actions is False and each run must vouch for
itself. A run needs a bug id and a known team.
@alastor0325

Copy link
Copy Markdown
Member Author

I had a short discussion with Paul today. I’m thinking about which parts could become shared tools or move in-tree to benefit other tools, as I’m also working on another PR to let the bugfix agent support more customized implementation workflows. I’ll share another update as this progresses.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants