plan-backlog — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited plan-backlog (Agent Skill) and scored it 100/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 0 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 0 flagged
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
Fetches open GitHub Issues, scores each with RICE (Reach × Impact × Confidence ÷ Effort), and outputs a ranked priority table. READ-ONLY — writes only to agent/state/backlog.json.
HALT check — if config.safety.halt_file exists: print [HALT] plan-backlog stopped. Reason: {content} and exit.
gh check — run gh --version. If unavailable:
gh CLI not available. Skipping plan-backlog.
Install: https://cli.github.com | Auth: gh auth loginExit cleanly (not an error).
Remote check — before fetching issues, verify a GitHub remote exists:
git remote -v 2>/dev/null | grep -qE 'github\.com[:/]'This checks for any remote pointing to GitHub (regardless of remote name — origin, upstream, etc.) and rejects non-GitHub remotes (GitLab, Bitbucket, etc.) that would cause gh to fail with a confusing error.
If no GitHub remote is found:
[plan-backlog] No GitHub remote configured. Backlog scoring requires a GitHub repository with issues. Skipping."status": "no_remote" (preserve and increment run_count if state already exists)EVERY early-exit state write (no_remote, no_issues, fetch/parse error) MUST also include "actionable_items": 0, "top_rice_score": 0.0 — evolve's 4-B chain trigger evaluates those fields (actionable_items >= 1 AND top_rice_score >= 50); omitting them leaves the condition undecidable instead of cleanly false.
gh issue list --state open --json number,title,labels,body,createdAt,assignees --limit 100On command error → Could not fetch issues. Is this a GitHub repository? Skipping. — exit 0. On malformed JSON (parse error) → treat identically to command error: log Could not parse gh output. Skipping. — exit 0. On empty array → write state with status: "no_issues", print No open issues to score. — exit 0.
Also read agent/state/backlog.json (if it exists) to carry forward run_count.
Body cap: only the first 2000 characters of each issue body are considered for scoring (avoids runaway cost on mega-issues with embedded logs).
Deduplication: before scoring, group issues whose titles share >=80% similarity (case-insensitive Levenshtein ratio). Within each group, keep only the lowest-numbered (oldest) issue; mark the rest "deduplicated": true in the state scores array and set their rice_score to 0. The report notes: N duplicate issues collapsed.
For each issue estimate four components from title, labels, and body.
| Component | Range | Label signals (highest match wins) | Default |
|---|---|---|---|
| Reach | 0.0–1.0 | user-facing/ux/frontend → 0.8, api/perf → 0.6, internal/chore → 0.2 | 0.5 |
| Impact | 0.25–3.0 | critical/P0 → 3.0, bug/security → 2.0, enhancement/P1 → 1.0, P2/low → 0.5 | 1.0 |
| Confidence | 0.5–1.0 | ≥3 labels + body>200 → 1.0, ≥1 label or body>100 → 0.8, bare issue → 0.5 | 0.8 |
| Effort | 1–10 days | easy/S → 1, L/needs-design or body>500 → 5, epic/XL → 8 | 3 |
Guard: Effort MUST be clamped to [1, 10] (never zero — prevents division-by-zero). When all issues share identical labels (or have no labels at all), every issue receives the same defaults; this is expected — relative ordering then falls back to Impact and Reach heuristics derived from the title and body text.
RICE = (Reach × Impact × Confidence) / Effort × 100 [round to 2 decimal places]Sort by RICE descending. Display the top 25 issues in the table (print ... and N more scored issues (see backlog.json) if truncated).
plan-backlog — <ISO timestamp> Scored: N issues (showing top 25)
| # | Title | RICE | R | I | C | E | Labels |
|-----|-----------------------------------------------|-------|-----|-----|-----|-----|-----------------|
| 42 | Fix login redirect loop | 53.33 | 0.8 | 2.0 | 1.0 | 3 | bug, P0 |Truncate titles to 45 chars with .... Truncate the Labels column to 20 chars with ... to keep rows aligned when issues carry many labels.
Write to agent/state/backlog.json (create agent/state/ if missing):
{ "schema_version": "1.0.0", "last_run": "<ISO 8601>", "run_count": 1,
"scored_count": 12, "unscored_count": 0, "status": "scored",
"actionable_items": 12, "top_rice_score": 53.33,
"duplicates_collapsed": 2,
"scores": [{ "number": 42, "title": "Fix login redirect loop",
"rice_score": 53.33, "reach": 0.8, "impact": 2.0, "confidence": 1.0,
"effort": 3, "labels": ["bug", "P0"], "created_at": "<ISO 8601>",
"deduplicated": false }] }Every issue is scored (defaults applied when labels/body absent). status: "scored", "no_issues", or "no_remote".
The state MUST also include two top-level summary fields consumed by chain triggers:
"actionable_items": 12,
"top_rice_score": 53.33actionable_items = count of scores where rice_score > 0. top_rice_score = maximum rice_score across all scored issues (0.0 when no issues).
Top 5 issues by RICE:
1. #42 Fix login redirect loop (RICE 53.33) — bug, P0
2. #7 Add dark mode toggle (RICE 13.33) — enhancement
...
Recommendation: Start with #42. High-impact bug affecting most users.
Chain trigger will fire on next /evolve when top RICE > 50.List all issues if fewer than 5. If none: No open issues to score. Backlog is clear.
| Scenario | Behavior |
|---|---|
| HALT file present | Print reason, exit immediately |
gh not installed | Print install hint, exit 0 |
| No GitHub remote configured | Write status: "no_remote", print message, exit 0 |
| Not a GitHub repo | Print message, exit 0 |
| Malformed gh JSON output | Log parse-error message, exit 0 |
| No open issues | Write status: "no_issues", exit 0 |
| Issue has no labels or body | Apply all defaults; still scored |
agent/state/ missing | Create directory, then write |
backlog.json corrupt | Re-initialize as first run |
~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.