@thehammer/danx-dashboard-mcp 0.1.7 → 0.1.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  import { describe, it, expect } from "vitest";
2
2
  import { DashboardHttpClient } from "./http-client.js";
3
- import { issueList } from "./handlers.js";
3
+ import { issueList, issueTransition } from "./handlers.js";
4
4
  /**
5
5
  * `issue_list` query-param forwarding. A fake `fetch` captures the built
6
6
  * URL so each filter is asserted at the wire, through the real client's
@@ -28,3 +28,24 @@ describe("issueList — query forwarding", () => {
28
28
  expect(urls[0]).toContain("include_closed=true");
29
29
  });
30
30
  });
31
+ describe("issueTransition — body forwarding", () => {
32
+ function clientCapturingBody() {
33
+ const bodies = [];
34
+ const fetchImpl = (async (_url, init) => {
35
+ bodies.push(JSON.parse(String(init?.body ?? "{}")));
36
+ return new Response(JSON.stringify({ issue: {} }), { status: 200 });
37
+ });
38
+ const client = new DashboardHttpClient({ baseUrl: "http://localhost:5555", repo: "danxbot", token: "t" }, fetchImpl);
39
+ return { client, bodies };
40
+ }
41
+ it("forwards manual: true on pickup (DX-946 operator self-pickup)", async () => {
42
+ const { client, bodies } = clientCapturingBody();
43
+ await issueTransition(client, { id: "DX-1", action: "pickup", manual: true });
44
+ expect(bodies[0]).toEqual({ action: "pickup", manual: true });
45
+ });
46
+ it("omits manual when not provided", async () => {
47
+ const { client, bodies } = clientCapturingBody();
48
+ await issueTransition(client, { id: "DX-1", action: "pickup" });
49
+ expect(bodies[0]).toEqual({ action: "pickup" });
50
+ });
51
+ });
package/dist/index.js CHANGED
@@ -155,12 +155,13 @@ server.tool("issue_edit", "Patch prose fields only via PATCH /api/issues/:id/edi
155
155
  ...repoField,
156
156
  }, async (args) => jsonResult(await issueEdit(client, args)));
157
157
  // ---------------- issue_transition ----------------
158
- server.tool("issue_transition", "Stamp a lifecycle transition via POST /api/issues/:id/transition. **THIS IS THE ONLY WAY TO MOVE A CARD'S LIFECYCLE STATE** — DX-835 separated card lifecycle (this tool) from dispatch finalization (`mcp__danxbot__danxbot_complete`). The worker no longer infers card moves from `danxbot_complete.status`; agents that want the card to move MUST call this tool BEFORE calling `danxbot_complete`. Actions: ready (Review→ToDo), pickup (ToDo→In Progress — server checks every dispatch gate: ready_at, blocked_at, requires_human_reason, depends_on partners terminal, conflict_on partners idle; refuses 409 with failed_gate naming the cause), rollback_pickup, **complete** (stamps completed_at — moves card to Done; this is YOUR explicit decision, not a side effect of danxbot_complete; REFUSES 409 on Epic if any phase child non-terminal — see non_terminal_phases[]), cancel (stamps cancelled_at — terminal), **block** (requires non-empty reason — stamps blocked_at + blocked_reason + clears dispatch; USE THIS when the CARD itself cannot proceed without human intervention; distinct from env-fault dispatch failures which use `danxbot_complete({status:'failed'})`), unblock, archive (parks to Backlog, clears ready_at), reopen (terminal→active, clears completed_at/cancelled_at/archived_at). Terminal cards refuse every action except reopen. Ladder timestamps preserved — forward stamps never clear earlier ones (CLAUDE.md Core Principle 2).", {
158
+ server.tool("issue_transition", "Stamp a lifecycle transition via POST /api/issues/:id/transition. **THIS IS THE ONLY WAY TO MOVE A CARD'S LIFECYCLE STATE** — DX-835 separated card lifecycle (this tool) from dispatch finalization (`mcp__danxbot__danxbot_complete`). The worker no longer infers card moves from `danxbot_complete.status`; agents that want the card to move MUST call this tool BEFORE calling `danxbot_complete`. Actions: ready (Review→ToDo), pickup (ToDo→In Progress — server checks every dispatch gate: ready_at, blocked_at, requires_human_reason, depends_on partners terminal, conflict_on partners idle; refuses 409 with failed_gate naming the cause; pass manual:true for OPERATOR-SESSION self-pickup — stamps dispatch_kind 'manual', bypasses every card-flow gate except terminal/deleted/already-dispatched, and the worker NEVER auto-transitions the card: no orphan-heal rollback, no Epic auto-rollup — use this whenever the work happens in YOUR current session rather than a worker dispatch, DX-946), rollback_pickup, **complete** (stamps completed_at — moves card to Done; this is YOUR explicit decision, not a side effect of danxbot_complete; REFUSES 409 on Epic if any phase child non-terminal — see non_terminal_phases[]), cancel (stamps cancelled_at — terminal), **block** (requires non-empty reason — stamps blocked_at + blocked_reason + clears dispatch; USE THIS when the CARD itself cannot proceed without human intervention; distinct from env-fault dispatch failures which use `danxbot_complete({status:'failed'})`), unblock, archive (parks to Backlog, clears ready_at), reopen (terminal→active, clears completed_at/cancelled_at/archived_at). Terminal cards refuse every action except reopen. Ladder timestamps preserved — forward stamps never clear earlier ones (CLAUDE.md Core Principle 2).", {
159
159
  id: z.string().min(1),
160
160
  action: z.enum(TRANSITION_ACTIONS),
161
161
  reason: z.string().optional(),
162
162
  summary: z.string().optional(),
163
163
  dispatch_id: z.string().min(1).optional(),
164
+ manual: z.boolean().optional(),
164
165
  ...repoField,
165
166
  }, async (args) => jsonResult(await issueTransition(client, args)));
166
167
  // ---------------- issue_triage ----------------
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thehammer/danx-dashboard-mcp",
3
- "version": "0.1.7",
3
+ "version": "0.1.8",
4
4
  "description": "Stdio MCP server wrapping danxbot's dashboard /api/issues/* normalized DB-backed HTTP routes for dispatched agents (DX-704 Phase 2).",
5
5
  "license": "MIT",
6
6
  "type": "module",