update_project
Update fields on an existing project: reassign party, owner, team, stage, or set custom fields. Use status='CLOSED' to close a project.
Instructions
Update fields on an existing project, including the parent-reference field partyId to reassign the project to a different primary party. ownerId, teamId, and stageId all accept null to unassign (the latter removes the project from all stages — verified empirically in v1.6.5 wire-trace). Constraint: a project must always have at least one of {owner, team} set, so teamId: null on a project with no owner returns 422. Only the fields you provide are changed. Use status='CLOSED' to close a project. CLOSED projects remain fully editable — Capsule does not enforce closed-record immutability. Stage moves and description edits on a CLOSED project are accepted without warning. Capsule requires every project to have a party — passing partyId: null is rejected with 422 'party is required' (Unlike update_task.partyId which IS nullable — tasks can be orphaned in Capsule's model).
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| id | No | ||
| name | No | ||
| description | No | ||
| status | No | ||
| partyId | No | Reassign the project to a different primary party. Capsule requires every project to have a party — passing `null` is rejected with 422 'party is required' (verified empirically in v1.6.3 wire-trace). Discover ids via search_parties / filter_parties. NOTE: parent-ref nullability differs by entity — `update_task.partyId` IS nullable (orphan task), but opportunities and projects must always have a parent party. The same applies to `update_opportunity.partyId`. | |
| ownerId | No | Reassign owner: pass a user ID to set, or `null` to unassign (matches the 'Unassign' option in Capsule's web UI). When you supply `ownerId` and omit `teamId` and/or `stageId`, the connector fetches the project's current omitted fields and includes them in the PUT body — this preserves them across the owner change (without it, Capsule's PUT would clear team; stage carry is defensive against the symmetric clear). Supply `teamId` and/or `stageId` explicitly on the same call to change them instead. `teamId: null` clears the team as part of an owner change. Constraints (Capsule enforces, 422 on violation): owner must be a member of the team if both are set; a project must always have at least one of {owner, team} set (cannot clear both). | |
| teamId | No | Reassign team: pass a team ID (discover via list_teams) to set, or `null` to unassign. Capsule preserves the existing owner across a team change (server-side), so `update_project { teamId }` alone is safe — the owner is carried through. Owner must be a member of the new team or Capsule returns 422 'owner is not a member of the team'. A project must always have at least one of {owner, team} set — `teamId: null` on a project whose owner is already null returns 422 'owner or team is required'. | |
| stageId | No | Move the project to this stage (board column), or `null` to remove from all stages (verified empirically in v1.6.5 wire-trace — Capsule accepts `stage: null` on PUT /kases/:id and the project no longer appears on any board). Discover IDs via list_stages. Owner and team are preserved across stage-only updates (Capsule's PUT semantic). WARNING (cross-board): Capsule does NOT validate that the new stage belongs to the project's current board — passing a stageId from a different board silently relocates the project across boards. Team and other board-derived defaults are NOT updated to match the new board. Verify against the project's current board (read the project first, list its board's stages) before passing a cross-board id. | |
| expectedCloseOn | No | YYYY-MM-DD | |
| fields | No | Set custom field values on this record. PARTIAL UPDATE: only the definitions you list are touched; any field NOT in this array is left unchanged. Discover available definitions via list_custom_fields; read current values via get_project with embed='fields'. Project-specific: setting a field whose definition lives under a 'data tag' populates the row's internal tagId but does NOT auto-add the data tag to the project's tags array — use add_tag explicitly if you want it visible via embed=tags. |