---
title: "Patch Project Data"
method: PATCH
path: "/api/projects/{project_id}/data"
tags: ["Projects"]
---

# Patch Project Data

`PATCH /api/projects/{project_id}/data`

## Request

- Base URL: `https://api.agentstack.tech` (the document declares no server; this is the origin it was published from)
- URL: `https://api.agentstack.tech/api/projects/{project_id}/data`
- Auth: one of:
  - API key in header `X-API-Key`
  - HTTP bearer

Update project.data at a dot path (ops, write_mode, dry_run, expected_sha256 CAS).

## Path parameters

- `project_id` integer, required

## Headers

- `Idempotency-Key` string

## Request body

- ProjectDataPatchBody: Leaf write on project.data (MCP parity: projects.patch_data).
  - `path` string, nullable: Dotted path into project.data (wins over patches[] when set)
  - `patches` ProjectDataPatchLeafItem[], nullable: Up to 16 leaves when path is omitted (plain replace SET may be atomic)
    - `path` string, required: Dotted path into project.data
    - `value` unknown
  - `value` unknown
  - `write_mode` string, nullable: replace | merge | delete | search_replace | fuzzy_replace | unified_diff | append | prepend
  - `allow_shrink` boolean: Allow deliberate shorter string (not read-window write-back)
  - `replacements` object[], nullable: search_replace pairs on a string leaf (merged into value).
  - `unified_diff` string, nullable: Unified diff on a string leaf (fuzzy unless strict_diff=true).
  - `strict_diff` boolean, nullable: Strict unified_diff apply (no fuzzy fallback).
  - `ops` object[], nullable: Up to 16 directed edit ops on the path leaf (merge, search_replace, insert_after, …).
  - `dry_run` boolean: Preview without writing DNA: directed ops or leaf write_mode (search_replace, merge, replace, …) returns leaf_sha256.
  - `expected_sha256` string, nullable: Optimistic concurrency digest of the leaf before ops.
  - `missing` string, nullable: When a path op misses: error | skip.

## Response `200`

Successful Response

- ProjectDataPatchResponse: PATCH project/member data leaf — MCP parity with projects.patch_data.
  - `success` boolean
  - `project_id` integer, required
  - `path` string, nullable: Primary leaf path (single-leaf); first leaf when batch writes[]
  - `writes` object[], nullable: Per-leaf results for multi-path PATCH (MCP parity)
  - `dry_run` boolean, nullable
  - `previous_sha256` string, nullable: Pre-mutation leaf digest; pass as expected_sha256 on commit after dry_run.
  - `leaf_sha256` string, nullable: Post-preview or post-write leaf digest.
  - `next_actions` object[], nullable: Suggested MCP/REST commit steps after dry_run (single-leaf CAS v1).
  - `preview_only` boolean, nullable: True when dry_run preview did not persist DNA.
  - `state` string, nullable: Mutation receipt state (e.g. previewed).
  - `write` object, nullable

## Other responses

- `400`: Bad Request
- `401`: Unauthorized
- `403`: Forbidden
- `404`: Not Found
- `409`: Conflict
- `422`: Validation Error
- `429`: Too Many Requests
- `500`: Internal Server Error

---

[API](https://skmtc.dev/agentstack/apis/agentstack-core-api.md) · [All operations](https://skmtc.dev/agentstack/apis/agentstack-core-api/llms.txt) · [OpenAPI document](https://skmtc.dev/agentstack/apis/agentstack-core-api/revisions/8ecf3406e74a?raw)
