> Source: https://wexa.ai/docs/context/delete-context

# delete-context

[Can be held for approval](/docs/sdks-and-apis/how-every-tool-call-works#lifecycle-and-governance)

Delete nodes from the project's context graph, with their relationships. Irreversible. Needs the `fabric:ontology.write` grant.

**Delete a node**

**Wexa MCP server**

```bash
curl -sS -X POST https://fabric.wexa.ai/mcp/$FABRIC_PROJECT_ID \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "Mcp-Session-Id: $MCP_SESSION_ID" \
  -H "content-type: application/json" -H "accept: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/call","params":{"name":"delete-context","arguments":{"label":"FixtureCustomer","key":"id","value":"c-1001"}}}'
```

```json
{
  "content": [
    {
      "type": "text",
      "text": "{\"lifecycle_id\":\"qlc_000213\",\"result\":{\"deleted\":1,\"element_ids\":[\"360525967589900288\"],\"label\":\"FixtureCustomer\",\"relationships\":\"detached with the node(s)\"}}"
    }
  ],
  "isError": false
}
```

**REST API**

```bash
curl -sS https://fabric.wexa.ai/v1/delete-context \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "content-type: application/json" \
  -d '{"label":"FixtureCustomer","key":"id","value":"c-1001"}'
```

```json
{
  "lifecycle_id": "qlc_000213",
  "result": {
    "deleted": 1,
    "element_ids": [
      "360525967589900288"
    ],
    "label": "FixtureCustomer",
    "relationships": "detached with the node(s)"
  }
}
```

**TypeScript SDK**

```ts
import { Fabric } from '@wexa-fabric/sdk'

const fabric = new Fabric()
const result = await fabric.deleteContext({
  label: 'FixtureCustomer',
  key: 'id',
  value: 'c-1001'
})
```

```ts
// result is the payload itself, with no `.result` to read
{
  deleted: 1,
  element_ids: [ '360525967589900288' ],
  label: 'FixtureCustomer',
  relationships: 'detached with the node(s)'
}
```

**Python SDK**

```python
from wexa import Fabric

fabric = Fabric()
out = fabric.delete_context(
    label="FixtureCustomer",
    key="id",
    value="c-1001",
)
```

```python
# out is the result, already unwrapped
{
    "deleted": 1,
    "element_ids": ["360525967589900288"],
    "label": "FixtureCustomer",
    "relationships": "detached with the node(s)"
}
```

## Parameters

| Parameter | Type | Required | Notes |
| --- | --- | --- | --- |
| `label` | string | Required | The nodes' label, for example `Customer`. Platform-managed labels cannot be deleted. |
| `key` | string | Optional | The merge-key property name, for example `id`. Needed with `value` or `values`. A plain identifier. |
| `value` | any | Optional | One merge-key value. Not null. Give exactly one of `value`, `values`, `where` or `all`. |
| `values` | array | Optional | A list of merge-key values, up to 10,000. Not empty; more than 10,000 is refused (413) and nothing is deleted, so split the delete. |
| `where` | object | Optional | Property-equality filter, for example `{"batch": "load-7"}`. A non-empty object. |
| `all` | boolean | Optional | `true` deletes every node of the label that `save-context` wrote. |
| `dry_run` | boolean | Optional | `true` returns `would_delete` and deletes nothing. Never held for approval. |
| `expected_count` | integer | Optional | Refuse the delete (409) unless exactly this many nodes match. Nothing is deleted on a mismatch. |

**Errors**

- `NotFound` (404): nothing you wrote matches. Answered before any approval is requested.
- `ValidationError` (422): not exactly one of `value`, `values`, `where` or `all` was given.

**Show full response**

A real response, captured from a live call to `delete-context`:

**Result of delete-context**

**REST API**

```json
{
  "lifecycle_id": "qlc_000213",
  "result": {
    "deleted": 1,
    "element_ids": [
      "360525967589900288"
    ],
    "label": "FixtureCustomer",
    "relationships": "detached with the node(s)"
  }
}
```

**Wexa MCP server**

```json
{
  "content": [
    {
      "type": "text",
      "text": "{\"lifecycle_id\":\"qlc_000213\",\"result\":{\"deleted\":1,\"element_ids\":[\"360525967589900288\"],\"label\":\"FixtureCustomer\",\"relationships\":\"detached with the node(s)\"}}"
    }
  ],
  "isError": false
}
```

**TypeScript SDK**

```ts
// the object you get back IS the result — there is no `.result` to read
{
  deleted: 1,
  element_ids: [ '360525967589900288' ],
  label: 'FixtureCustomer',
  relationships: 'detached with the node(s)'
}

// The TS SDK names these camelCase — lifecycleId, traceId — where Python uses
// lifecycle_id and trace_id. Both are non-enumerable: readable, but omitted by
// Object.keys() and JSON.stringify(). `result.lifecycleId` here is undefined.
result.lifecycleId // 'qlc_000213'
```

**Python SDK**

```python
# a dict subclass; `result` is already unwrapped
{
 "deleted": 1,
 "element_ids": [
  "360525967589900288"
 ],
 "label": "FixtureCustomer",
 "relationships": "detached with the node(s)"
}

out.lifecycle_id  # 'qlc_000213' — an attribute, not a key
```

**More details**

Full description from the tool, as the gateway advertises it:

Delete nodes from this project's context graph, together with their relationships. Address them as you wrote them with save-context: a `label` plus exactly one of `value`, `values`, `where` or `all`. Up to 10,000 nodes per call, under one approval when the call is held; `dry_run: true` returns the count without deleting and is never held. Deleting is permanent and there is no undo, so this reports how many nodes matched — if it matched nothing you get an error, not a cheerful success. Platform-managed labels cannot be deleted through this tool. query-context refuses DELETE/DETACH on purpose; this is the only delete path.

Marked consequential: it is audited in full, and a policy rule or the write gate may hold it for a person to approve. One approval covers every node the call matched. See [Policy and approvals](/docs/governance/policy-and-approvals).

Every tool call works the same way: [How every tool call works](/docs/sdks-and-apis/how-every-tool-call-works).
