{
  "openapi": "3.1.0",
  "info": {
    "title": "Hark API",
    "license": {
      "name": "Hark API Terms",
      "url": "https://harkstudio.io/terms"
    },
    "version": "0.1.0",
    "description": "REST mirror of Hark's MCP tools for agents that can only call HTTP APIs. Same access keys, rate limits, sessions and proposal rules as harkstudio.io/mcp. Anything an agent writes is a proposal until a human accepts it in Hark."
  },
  "servers": [
    {
      "url": "https://harkstudio.io/api/v1"
    }
  ],
  "security": [
    {
      "accessKey": []
    }
  ],
  "components": {
    "securitySchemes": {
      "accessKey": {
        "type": "apiKey",
        "in": "header",
        "name": "Authorization",
        "description": "Authorization: Bearer hark_pat_… (create one at harkstudio.io/connections; read-only keys can't write)."
      }
    },
    "schemas": {
      "Error": {
        "type": "object",
        "properties": {
          "error": {
            "type": "string"
          },
          "message": {
            "type": "string"
          }
        },
        "required": [
          "error",
          "message"
        ]
      }
    }
  },
  "paths": {
    "/me": {
      "get": {
        "operationId": "getMe",
        "summary": "The key's user and workshops.",
        "description": "List every workspace the caller belongs to, with id, name, slug, role, plan, and comped flag. Use the id (or slug) as workspace_id in other tools when you belong to more than one workspace.\n\nMirrors the MCP tool `list_workspaces`.",
        "parameters": [
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "list_workspaces"
      }
    },
    "/projects": {
      "get": {
        "operationId": "getProjects",
        "summary": "List projects.",
        "description": "List ventures in a workspace with code, title, one-liner, stage, tags, and last updated time. Pass workspace_id (uuid or slug) when you belong to more than one workspace. Optionally filter by stage or include archived.\n\nMirrors the MCP tool `list_ventures`.",
        "parameters": [
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          },
          {
            "name": "workspace_id",
            "in": "query",
            "required": false,
            "schema": {
              "description": "Workspace uuid or slug. Optional.",
              "type": "string"
            }
          },
          {
            "name": "stage",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "vault",
                "recon",
                "blueprint",
                "fabrication",
                "live",
                "cold_storage"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "list_ventures"
      },
      "post": {
        "operationId": "postProjects",
        "summary": "Create a project. Without workspace_id or new_workspace_name nothing is created and your workshops are returned so you can ask which one.",
        "description": "Create a new project. ALWAYS ask the user first which workshop it belongs in, or whether to create a new workshop for it. Pass workspace_id (uuid or slug) for an existing workshop, or new_workspace_name to create a new workshop owned by the user and put the project in it. If neither is passed, nothing is created: the tool returns the user's workshops so you can ask.\n\nMirrors the MCP tool `create_venture`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "create_venture",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "title": {
                    "type": "string",
                    "minLength": 1,
                    "description": "Short name for the project."
                  },
                  "one_liner": {
                    "description": "One-breath description.",
                    "type": "string"
                  },
                  "stage": {
                    "description": "Starting stage. Defaults to 'vault'.",
                    "type": "string",
                    "enum": [
                      "vault",
                      "recon",
                      "blueprint",
                      "fabrication",
                      "live",
                      "cold_storage"
                    ]
                  },
                  "tags": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  },
                  "workspace_id": {
                    "description": "Existing workshop uuid or slug the user chose.",
                    "type": "string"
                  },
                  "new_workspace_name": {
                    "description": "Create a new workshop with this name and put the project in it.",
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 80
                  }
                },
                "required": [
                  "title"
                ],
                "additionalProperties": false
              },
              "example": {
                "title": "Meal planner",
                "workspace_id": "my-projects"
              }
            }
          }
        }
      }
    },
    "/projects/{code}": {
      "get": {
        "operationId": "getProjectsCode",
        "summary": "Get a project.",
        "description": "Fetch a full venture project by uuid or V-### code, including all Business/Build/Branding fields, CLAUDE.md, and the readiness checklist. Call this first to load context before editing.\n\nMirrors the MCP tool `get_venture`.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "get_venture"
      }
    },
    "/projects/{code}/brief": {
      "get": {
        "operationId": "getProjectsCodeBrief",
        "summary": "Read the project brief. Call this first.",
        "description": "Call this at the start of every session before doing work. Default is a COMPACT brief (~1,500 tokens): identity line, handoff status (including any unconfirmed draft handoff from a session that stopped without end_session), Current state (phase, summary, next up, blockers, non-goals, kill criterion), the last 3 accepted decisions, the count of unreviewed agent proposals, and a one-line primary repo status. Request depth='full' only when you need the whole project (AI context doc, session handoffs, all decisions, features, checklist, sparks). Reading the brief binds your session to this venture — other ventures are rejected until you call switch_venture.\n\nMirrors the MCP tool `get_agent_brief`.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          },
          {
            "name": "depth",
            "in": "query",
            "required": false,
            "schema": {
              "description": "Defaults to compact.",
              "type": "string",
              "enum": [
                "compact",
                "full"
              ]
            }
          },
          {
            "name": "task",
            "in": "query",
            "required": false,
            "schema": {
              "description": "What you're about to work on (e.g. 'billing'). Records matching the task rank first; accepted project-wide decisions and blockers are always included; proposals stay in a separate unreviewed section.",
              "type": "string",
              "maxLength": 500
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "get_agent_brief"
      }
    },
    "/projects/{code}/decisions": {
      "get": {
        "operationId": "getProjectsCodeDecisions",
        "summary": "List decisions.",
        "description": "List a venture's journal entries (Ship Log, Decisions and agent session handoffs). Filter by kind ('ship', 'decision' or 'session') or omit to get all. Ordered newest first. Session entries are private to the workshop.\n\nMirrors the MCP tool `list_journal_entries`.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 200
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "list_journal_entries"
      },
      "post": {
        "operationId": "postProjectsCodeDecisions",
        "summary": "Record a decision. Creates a proposal; a human accepts it in Hark.",
        "description": "Add a Ship Log or Decision entry to a venture. kind='ship' for shipped work, kind='decision' for decisions with rationale. occurred_at defaults to now. Use during a session as decisions are made and work completes — do not batch everything into CLAUDE.md. Decisions written by an agent are recorded as candidates (proposals) until a human accepts them; they appear in a separate 'unreviewed' block in the brief and never on public project pages.\n\nMirrors the MCP tool `add_journal_entry`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "add_journal_entry",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "rejected_alternatives": {
                    "description": "Decisions only: options considered and why each was rejected.",
                    "maxItems": 6,
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "option": {
                          "type": "string",
                          "minLength": 1,
                          "maxLength": 200
                        },
                        "why": {
                          "type": "string",
                          "maxLength": 300
                        }
                      },
                      "required": [
                        "option"
                      ]
                    }
                  },
                  "attempt": {
                    "description": "Required for kind='attempt'.",
                    "type": "object",
                    "properties": {
                      "tried": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 300
                      },
                      "outcome": {
                        "type": "string",
                        "enum": [
                          "failed",
                          "partial",
                          "worked"
                        ]
                      },
                      "wrong_because": {
                        "type": "string",
                        "maxLength": 400
                      },
                      "do_instead": {
                        "type": "string",
                        "maxLength": 400
                      },
                      "evidence": {
                        "maxItems": 6,
                        "type": "array",
                        "items": {
                          "type": "object",
                          "properties": {
                            "label": {
                              "type": "string",
                              "maxLength": 120
                            },
                            "url": {
                              "type": "string",
                              "format": "uri"
                            }
                          },
                          "required": [
                            "label",
                            "url"
                          ]
                        }
                      }
                    },
                    "required": [
                      "tried",
                      "outcome"
                    ]
                  },
                  "title": {
                    "type": "string",
                    "minLength": 1
                  },
                  "body": {
                    "type": "string"
                  },
                  "rationale": {
                    "description": "Only used for kind='decision'.",
                    "type": "string"
                  },
                  "supersedes": {
                    "description": "Journal entry ids this decision explicitly replaces. Declaring them here is the authoritative path: they are marked superseded when the decision is accepted. Never guess — only pass ids you were told about or read from list_journal_entries.",
                    "maxItems": 10,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "uuid",
                      "pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"
                    }
                  },
                  "occurred_at": {
                    "description": "ISO datetime; defaults to now.",
                    "type": "string"
                  }
                },
                "required": [
                  "title"
                ],
                "additionalProperties": false
              },
              "example": {
                "title": "Use Postgres, not Mongo",
                "rationale": "Relational data; RLS."
              }
            }
          }
        }
      }
    },
    "/projects/{code}/needs-you": {
      "get": {
        "operationId": "getProjectsCodeNeedsYou",
        "summary": "List what's waiting for a human to review.",
        "description": "List everything agents have proposed on this venture that a human has not reviewed yet: decision entries and proposed Current state fields (phase, summary, blockers). Candidates are excluded from public project pages and shown separately in the brief.\n\nMirrors the MCP tool `list_candidates`.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "list_candidates"
      }
    },
    "/projects/{code}/notes": {
      "post": {
        "operationId": "postProjectsCodeNotes",
        "summary": "Add a note (a claim, shown as Note — never Observed). Creates a proposal; a human accepts it in Hark.",
        "description": "Add a Ship Log or Decision entry to a venture. kind='ship' for shipped work, kind='decision' for decisions with rationale. occurred_at defaults to now. Use during a session as decisions are made and work completes — do not batch everything into CLAUDE.md. Decisions written by an agent are recorded as candidates (proposals) until a human accepts them; they appear in a separate 'unreviewed' block in the brief and never on public project pages.\n\nMirrors the MCP tool `add_journal_entry`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "add_journal_entry",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "rejected_alternatives": {
                    "description": "Decisions only: options considered and why each was rejected.",
                    "maxItems": 6,
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "option": {
                          "type": "string",
                          "minLength": 1,
                          "maxLength": 200
                        },
                        "why": {
                          "type": "string",
                          "maxLength": 300
                        }
                      },
                      "required": [
                        "option"
                      ]
                    }
                  },
                  "attempt": {
                    "description": "Required for kind='attempt'.",
                    "type": "object",
                    "properties": {
                      "tried": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 300
                      },
                      "outcome": {
                        "type": "string",
                        "enum": [
                          "failed",
                          "partial",
                          "worked"
                        ]
                      },
                      "wrong_because": {
                        "type": "string",
                        "maxLength": 400
                      },
                      "do_instead": {
                        "type": "string",
                        "maxLength": 400
                      },
                      "evidence": {
                        "maxItems": 6,
                        "type": "array",
                        "items": {
                          "type": "object",
                          "properties": {
                            "label": {
                              "type": "string",
                              "maxLength": 120
                            },
                            "url": {
                              "type": "string",
                              "format": "uri"
                            }
                          },
                          "required": [
                            "label",
                            "url"
                          ]
                        }
                      }
                    },
                    "required": [
                      "tried",
                      "outcome"
                    ]
                  },
                  "title": {
                    "type": "string",
                    "minLength": 1
                  },
                  "body": {
                    "type": "string"
                  },
                  "rationale": {
                    "description": "Only used for kind='decision'.",
                    "type": "string"
                  },
                  "supersedes": {
                    "description": "Journal entry ids this decision explicitly replaces. Declaring them here is the authoritative path: they are marked superseded when the decision is accepted. Never guess — only pass ids you were told about or read from list_journal_entries.",
                    "maxItems": 10,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "uuid",
                      "pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"
                    }
                  },
                  "occurred_at": {
                    "description": "ISO datetime; defaults to now.",
                    "type": "string"
                  }
                },
                "required": [
                  "title"
                ],
                "additionalProperties": false
              },
              "example": {
                "title": "Checkout drops on Safari",
                "body": "Seen twice this week."
              }
            }
          }
        }
      }
    },
    "/projects/{code}/state": {
      "post": {
        "operationId": "postProjectsCodeState",
        "summary": "Propose Current state changes (phase, summary, next up, blockers…). Creates a proposal; a human accepts it in Hark.",
        "description": "Partial update of the venture's Current state — the living snapshot the app and every agent read first. Only the fields you pass are replaced; omit a field to leave it alone. Keep entries short (one line each). Changes to current_phase, summary and blockers are recorded as candidates (proposals) until a human accepts them; every other field applies immediately.\n\nMirrors the MCP tool `update_build_state`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "update_build_state",
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "current_phase": {
                    "description": "Short phase label, e.g. 'Beta hardening'. Proposed, not applied, until reviewed.",
                    "type": "string",
                    "maxLength": 80
                  },
                  "summary": {
                    "description": "2-3 sentences on where the build is right now. Proposed until reviewed.",
                    "type": "string",
                    "maxLength": 800
                  },
                  "just_shipped": {
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "in_progress": {
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "next_up": {
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "blockers": {
                    "description": "Proposed until reviewed.",
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "open_questions": {
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "non_goals": {
                    "description": "Things this venture deliberately will not do.",
                    "maxItems": 12,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "kill_criterion": {
                    "description": "'We stop if …' — required to leave the Vault stage.",
                    "type": "string",
                    "maxLength": 300
                  },
                  "next_review_date": {
                    "description": "ISO date for the next review — required to leave the Vault stage.",
                    "type": "string",
                    "maxLength": 40
                  }
                },
                "additionalProperties": false
              },
              "example": {
                "next_up": [
                  "Ship onboarding email"
                ]
              }
            }
          }
        }
      }
    },
    "/projects/{code}/sessions/start": {
      "post": {
        "operationId": "postProjectsCodeSessionsStart",
        "summary": "Start a work session; returns the compact brief and session_id.",
        "description": "Call this first, before any work. Opens a session bound to this one venture (calls naming a different venture are rejected until you call switch_venture), returns the compact brief, and records a 'session started' row attributed to your client. Pair it with end_session when you stop — otherwise Hark auto-drafts a handoff from your activity after 45 minutes of inactivity.\n\nMirrors the MCP tool `start_session`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "start_session",
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "depth": {
                    "description": "Defaults to compact.",
                    "type": "string",
                    "enum": [
                      "compact",
                      "full"
                    ]
                  }
                },
                "additionalProperties": false
              }
            }
          }
        }
      }
    },
    "/projects/{code}/sessions/end": {
      "post": {
        "operationId": "postProjectsCodeSessionsEnd",
        "summary": "End the session with a handoff note. What changed is recorded as proposed claims. Creates a proposal; a human accepts it in Hark.",
        "description": "Call this at the end of every session, before you stop. Writes a 'session' journal entry (What I did / What changed / What's next / Watch out for) and applies the implied Current state changes: what you say changed or shipped is recorded as a PROPOSED claim (a human accepts it; observed PRs/releases are recorded separately), and what's next is appended to next_up. Session entries are private to the workshop — they never appear on public project pages.\n\nMirrors the MCP tool `end_session`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "end_session",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "what_i_did": {
                    "type": "string",
                    "minLength": 1
                  },
                  "what_changed": {
                    "type": "string",
                    "minLength": 1,
                    "description": "One item per line — files, features, behaviour."
                  },
                  "whats_next": {
                    "type": "string",
                    "minLength": 1,
                    "description": "One item per line."
                  },
                  "watch_out_for": {
                    "description": "Gotchas the next session should know.",
                    "type": "string"
                  },
                  "features_touched": {
                    "maxItems": 20,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  },
                  "supersedes": {
                    "description": "Journal entry ids this session's outcome explicitly replaces (e.g. a decision reversed during the session). Applied immediately — only pass ids the user confirmed.",
                    "maxItems": 10,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "uuid",
                      "pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"
                    }
                  },
                  "links": {
                    "description": "PRs, files or URLs touched.",
                    "maxItems": 10,
                    "type": "array",
                    "items": {
                      "type": "string",
                      "minLength": 1
                    }
                  }
                },
                "required": [
                  "what_i_did",
                  "what_changed",
                  "whats_next"
                ],
                "additionalProperties": false
              },
              "example": {
                "what_i_did": "Wired the API",
                "what_changed": "api/v1 routes",
                "whats_next": "Write docs"
              }
            }
          }
        }
      }
    },
    "/projects/{code}/handoffs": {
      "post": {
        "operationId": "postProjectsCodeHandoffs",
        "summary": "Create a handoff link (recipient type, purpose). Returns the link.",
        "description": "Create a versioned handoff link for this project — the same thing the Hand off button makes. Choose who it's for (developer, client, agent) and a purpose. Returns the link. Only accepted records are shown; proposals never appear.\n\nMirrors the MCP tool `create_handoff`. Read-only keys get 403.",
        "parameters": [
          {
            "name": "code",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Project code (V-032) or uuid.",
            "example": "V-032"
          },
          {
            "name": "X-Hark-Conversation",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Idempotency key: every call with the same value shares one Hark session (mirrors MCP _meta.conversation)."
          },
          {
            "name": "X-Hark-Client",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Your product name, used for attribution (otherwise User-Agent)."
          }
        ],
        "responses": {
          "200": {
            "description": "Tool result (JSON).",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid arguments.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "401": {
            "description": "Missing, unknown, revoked or expired key.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "403": {
            "description": "Read-only key on a write.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "404": {
            "description": "Project not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        },
        "x-mcp-tool": "create_handoff",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "recipient": {
                    "type": "string",
                    "enum": [
                      "developer",
                      "client",
                      "agent"
                    ],
                    "description": "Who the handoff is for."
                  },
                  "recipient_label": {
                    "description": "Optional name, e.g. 'Sam (contract dev)'.",
                    "type": "string",
                    "maxLength": 120
                  },
                  "purpose": {
                    "description": "What the recipient should do next.",
                    "type": "string",
                    "maxLength": 2000
                  },
                  "repo_access": {
                    "description": "Whether the recipient already has repo access.",
                    "type": "boolean"
                  }
                },
                "required": [
                  "recipient"
                ],
                "additionalProperties": false
              },
              "example": {
                "recipient": "developer",
                "purpose": "Pick up the billing work"
              }
            }
          }
        }
      }
    }
  }
}