Backlog Methodology

Review & state-of-play

From a conflict-prone BACKLOG.md to a status-driven workflow on GitHub Issues + Projects + spec-kit.

DeepBlueCLtd / backlog-navigator · PR #3 · 2026-05-16

Where we started

A version-controlled BACKLOG.md works… until parallel work touches it.

  • Reorders, status changes, new items all collide on the same lines.
  • Two PRs in flight ⇒ guaranteed merge conflict on the backlog.
  • Every backlog tweak needs a code review, even when it has nothing to do with code.
  • The file fights against parallel work rather than for it.

Git is the right tool for source. It is the wrong tool for a live, multi-writer queue.

Objectives

  1. Eliminate merge conflicts on backlog edits.
  2. Couple the backlog to native GitHub — sub-issues, assignees, linked PRs, mobile, search.
  3. Let status changes drive real work, not just label it.
  4. Keep infrastructure small; contracts clear; nothing forks the agent ecosystem.

A successful design is one where dragging a card from Triage to In Design means something happens.

Strategy in one picture

flowchart TB
    subgraph driver [The driver]
        LP["/loop 15m"]
    end
    subgraph orch [Orchestration - this repo]
        BP["/backlog-poll"]
    end
    subgraph phases [Per-phase work - spec-kit]
        SP["/speckit-specify"]
        PL["/speckit-plan"]
        TK["/speckit-tasks"]
        TI["/speckit-taskstoissues"]
        IM["/speckit-implement"]
    end
    subgraph gh [GitHub primitives]
        PJ[Project board]
        IS[Issues + sub-issues]
        PRR[PRs]
    end

    LP --> BP
    BP -->|reads Status + Phase| PJ
    BP -->|writes Phase + Total| PJ
    BP --> SP
    BP --> PL
    BP --> TK
    BP --> TI
    BP --> IM
    SP --> PRR
    TI --> IS
    IM --> PRR

Four layers: driver → orchestrator → per-phase skills → GitHub. Each layer has a small, well-defined job.

The state machine

flowchart LR
    T["Triage"]:::triage --> D["In Design"]:::design
    D --> R["Ready"]:::ready
    R --> O["Doing"]:::doing
    O --> N["Done"]:::done

    classDef triage fill:#e8e8e8,stroke:#888,color:#333
    classDef design fill:#cfe2f3,stroke:#3b78a8,color:#1a3c5c
    classDef ready  fill:#d9d2e9,stroke:#674ea7,color:#3d2a6a
    classDef doing  fill:#fff2cc,stroke:#bf9000,color:#665300
    classDef done   fill:#d9ead3,stroke:#38761d,color:#1f4710
  • Maintainers drag cards. External contributors only file.
  • Each transition has a contract (next slide).
  • The orchestrator is woken by status changes, not by code.

Project schema

FieldTypeNotes
Statussingle-selectMaintainer-dragged: Triage / In Design / Ready / Doing / Done
Phasesingle-selectOrchestrator-maintained: Spec drafting → Plan drafting → Tasks drafting → (Decomposing) → Designed → Implementing
OwnertextWorker-claimed: e.g. bn-swift-mango-7234. Empty = unclaimed. Multiple workers cooperate via this field.
Categorysingle-selectFeature, Enhancement, Tech Debt, Bug, Documentation, Spike
Complexitysingle-selectLow / Medium / High
V, M, Anumbers3-dimensional priority score (0–5 each)
TotalnumberV + M + A, recomputed every tick

Public Project, one per repo. Status is the human kanban; Phase is the orchestrator's API-state source of truth — it stops re-triggers when a phase's work is sitting in an open PR.

Trigger contracts

What happens on each status change:

TransitionSkills invoked
In Design /speckit-specify/speckit-clarify (if ambiguous) → /speckit-plan/speckit-tasks
In Design (Epic only) …then /speckit-taskstoissues to file each task as a sub-issue
Doing /speckit-implement

Both transitions stop at PR open. Humans review spec and implementation content before merge. The agent saves typing, not judgement.

The orchestration loop

sequenceDiagram
    participant L as Loop
    participant P as Poll
    participant GH as Project
    participant SK as Phase
    participant U as User

    L->>P: tick (15min)
    P->>P: scan locks
    Note over P: skip if locked
    P->>GH: fetch state
    P->>GH: write Phase + Total
    P->>P: pick item
    P->>SK: run speckit
    alt blocked
        SK->>U: ask in chat
        P->>P: write lock, exit
    else completes
        SK->>GH: open PR
        P->>U: summary
    end

One item's journey

flowchart LR
    subgraph intake [Intake]
      direction TB
      A["Anyone files an issue
(minimal template)"] --> B["Auto-added to
Project as Triage"] --> C["Maintainer scores:
Category · Complexity · V/M/A"] end subgraph design [Design phase] direction TB D["Drag → In Design"] --> E["/backlog-poll runs
specify → clarify? → plan → tasks"] --> F["Design PR opens"] --> G["Maintainer reviews + merges"] end subgraph delivery [Delivery phase] direction TB H["Drag → Ready"] --> I["Drag → Doing
(when capacity)"] --> J["/backlog-poll runs
/speckit-implement"] --> K["Implementation PR opens"] --> L["Merge → issue closes,
status auto-→ Done"] end intake --> design --> delivery

All items go through specify → clarify? → plan → tasks in step E. Epics get one additional step — taskstoissues — that files each task as a sub-issue. Those sub-issues then flow through this same lifecycle.

Lock-file safety

How /loop avoids re-triggering when you're slow to answer:

sequenceDiagram
    participant T1 as Tick #1
    participant LF as .claude/in-flight/5.md
    participant U as Maintainer
    participant T2 as Tick #2 (15min later)

    T1->>LF: write lock (committed on feature branch)
    T1->>U: question in chat
    Note over U: ...away from desk...
    T2->>LF: scan for locks
    LF-->>T2: lock for #5 exists
    T2-->>T2: skip — no new work this tick
    U->>T1: (eventually) answers
    T1->>LF: delete lock
    T1->>U: summary in chat

Locks are committed, so cloud-CC container restarts pick up exactly where the previous session left off.

What we've built

Everything below is on PR #3, ready for your review:

  • METHODOLOGY.md — full methodology, 444 lines
  • spec-kit installed in this repo (.claude/skills/speckit-*, .specify/)
  • /backlog-poll skill at .claude/skills/backlog-poll/SKILL.md
  • Migration runbook at docs/migration/from-backlog-md.md
  • This presentation (docs/presentation/)

6 commits on claude/backlog-github-discussions-a59Xw. Zero impact on the existing navigator app — it still works during the transition.

What's still ahead

These steps are yours — they need GitHub credentials & UI access:

  1. GitHub Project created at orgs/DeepBlueCLtd/projects/4.
  2. .claude/backlog-poll.config.json pointing at Project #4.
  3. Phase field added to Project #4.
  4. Add the Owner field (text) to Project #4 — needed for the worker-pool model.
  5. Migrate the 9 dummy items from BACKLOG.md with Status + initial Phase (runbook step 7).
  6. Archive BACKLOG.md (runbook step 9).
  7. Open a Claude Code session & run /loop 15m /backlog-poll.
  8. Drag a card — see if the orchestrator picks it up.
  9. Iterate on /backlog-poll based on what breaks.

Known limits we're shipping with

  • Needs a live CC session running /loop. Cloud CC is the natural home.
  • ~15 min dispatch latency, bound by the loop interval.
  • No native GitHub trigger for project_v2_item.edited — polling is the workaround.
  • Speckit drift: pin to a release tag, re-init periodically, diff against your committed copies.
  • Project state isn't reproducible from git. If you need backlog snapshots, render to a file on a schedule.
  • Public Project on a private repo leaks titles. Check before flipping visibility.

Webhook-driven dispatch is possible later — methodology mentions it as a note. Not on the roadmap.

Adopting in other repos

Once we've validated here, the recipe for any other repo is short:

  1. Install spec-kit:
    uv tool run --from git+https://github.com/github/spec-kit.git \
        specify init . --integration claude --force
  2. Copy .claude/skills/backlog-poll/SKILL.md from this repo.
  3. Follow the migration runbook (Project + fields + issues).
  4. Write their .claude/backlog-poll.config.json.
  5. Run /loop 15m /backlog-poll in a CC session.

This repo stays the canonical reference for the methodology.

Next concrete step

Create the GitHub Project for DeepBlueCLtd/backlog-navigator and run the migration runbook on the 9 dummy items.

Then we have real data to point /backlog-poll at, and the testbed becomes live.

PR #3 is ready for your review meanwhile.