Skip to content

feat(api): scope pull_task / GET /work/next to a specific run_id #75

@viktor-shcherb

Description

@viktor-shcherb

Goal

Let an agent (Claude Code via the Murmur MCP server) drive a single Murmur run end-to-end without picking up unrelated stale or concurrent work that's also in the queue.

Why

The post-demo workflow on jobseek will let any user request a company be added; each request creates a Murmur run that sits in the queue waiting for an agent. When a user prompts their own Claude session "add Stripe to jobseek", that agent must claim only that run's subtasks. Without a run_id scope, pull_task returns the oldest ready row globally — likely some other user's pending request.

Also unblocks the demo: rehearsals leave stale claims in the queue that are FIFO'd ahead of fresh runs, breaking audience-facing dry-runs.

Scope

  1. New SQL CLAIM_BY_RUN_SQL in src/api/agent/sql.ts: same shape as CLAIM_SQL plus AND run_id = ? in the inner SELECT.
  2. GET /work/next accepts an optional ?run_id=... query param. When set, uses CLAIM_BY_RUN_SQL; otherwise legacy global FIFO.
  3. pull_task MCP tool gets an optional run_id: string arg. Description updated to explain the parameter. Forwards to GET /work/next?run_id=....

Interfaces

  • CLAIM_BY_RUN_SQL: string (export from sql.ts)
  • app.get("/next", ...) — reads c.req.query("run_id")
  • PULL_TASK_INPUT_SHAPE = { run_id: z.string().min(1).optional() }

Verification

  • Unit test: GET /work/next with no run_id claims oldest ready row globally (legacy).
  • Unit test: GET /work/next?run_id=r_X claims oldest ready row whose run_id == r_X, ignoring older ready rows from other runs.
  • Unit test: GET /work/next?run_id=r_unknown returns {ok:true, data:null}.
  • MCP test: pull_task with no args still works (legacy).
  • MCP test: pull_task({run_id: 'r_X'}) claims only that run's work.
  • All 3 existing pull_task / submit_result / task_tool tests in src/mcp/server.test.ts still pass.

Definition of done

  • Tests above all green.
  • pnpm typecheck && pnpm lint && pnpm test && pnpm grep:all clean.
  • PR opened referencing this issue, reviewer APPROVE.
  • DESIGN.md §3.3 / §3.4 updated to mention the optional run_id filter.

Out of scope

  • Listing runs or filtering by initial_input (separate issue).
  • Per-user ownership / authz on run access (post-demo).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions