> ## Documentation Index
> Fetch the complete documentation index at: https://mintlify.com/Gentleman-Programming/engram/llms.txt
> Use this file to discover all available pages before exploring further.

# mem_delete

> Delete an observation by ID

## Overview

Delete an observation by ID. Supports both **soft delete** (default, marks as deleted but keeps data) and **hard delete** (permanent removal).

<Warning>
  This tool is part of the **admin** profile and uses deferred loading. It's primarily for manual curation, TUI operations, and data cleanup — not typical agent workflows.
</Warning>

## Parameters

<ParamField path="id" type="number" required>
  Observation ID to delete

  Get the ID from:

  * [`mem_search`](/mcp/mem-search) results
  * [`mem_get_observation`](/mcp/mem-get-observation) response
  * [`mem_timeline`](/mcp/mem-timeline) results
  * TUI observation view

  **Example:** `42`
</ParamField>

<ParamField path="hard_delete" type="boolean">
  If `true`, permanently deletes the observation

  **Default:** `false` (soft delete)

  * **Soft delete:** Sets `deleted_at` timestamp, observation remains in database but excluded from search/context
  * **Hard delete:** Permanently removes the row from the database
</ParamField>

## Response

<ResponseField name="result" type="string">
  Confirmation message indicating deletion mode
</ResponseField>

**Soft delete:**

```
Memory #42 soft-deleted
```

**Hard delete:**

```
Memory #42 permanently deleted
```

## Usage Examples

### Soft Delete (Default)

```json theme={null}
{
  "id": 42
}
```

Marks observation #42 as deleted. The data remains in the database but is excluded from:

* `mem_search` results
* `mem_context` results
* `mem_timeline` results
* TUI views (unless "show deleted" is enabled)

<Tip>
  Soft deletes are **reversible** — you can manually update `deleted_at` to `NULL` in the database to restore.
</Tip>

### Hard Delete

```json theme={null}
{
  "id": 42,
  "hard_delete": true
}
```

Permanently removes observation #42 from the database. **This is irreversible.**

<Warning>
  Hard deletes are permanent. Use soft delete unless you're certain the data should be gone forever.
</Warning>

## When to Use

<AccordionGroup>
  <Accordion title="Soft Delete">
    Use soft delete when:

    * Removing test data
    * Hiding observations without losing history
    * Cleaning up noise from search results
    * Temporarily excluding data (reversible)

    **Advantages:**

    * Reversible — can restore by clearing `deleted_at`
    * Maintains audit trail
    * Safer for accidental deletions
  </Accordion>

  <Accordion title="Hard Delete">
    Use hard delete when:

    * Removing sensitive data that must be purged
    * Database cleanup to reduce size
    * Permanently removing incorrect data
    * GDPR or data retention compliance

    **Advantages:**

    * Actually removes data from disk
    * Reduces database size
    * Ensures data is gone

    **Disadvantages:**

    * Irreversible
    * No audit trail
  </Accordion>
</AccordionGroup>

## What Happens on Delete

### Soft Delete

1. Sets `deleted_at` timestamp to current time
2. Observation remains in `observations` table
3. Excluded from:
   * Search queries (`WHERE deleted_at IS NULL`)
   * Context queries
   * Timeline results
   * Default TUI views
4. Can be shown with "show deleted" filter in TUI
5. Database size unchanged

### Hard Delete

1. Row is permanently removed via `DELETE FROM observations WHERE id = ?`
2. FTS5 index entry is removed
3. No way to restore
4. Database size reduced (after `VACUUM`)

## Validation

<AccordionGroup>
  <Accordion title="ID must exist">
    If the observation ID doesn't exist, you'll get an error:

    ```
    Failed to delete memory: observation not found
    ```

    Use [`mem_search`](/mcp/mem-search) to find the correct ID.
  </Accordion>

  <Accordion title="Soft delete is idempotent">
    Soft-deleting an already soft-deleted observation succeeds (updates `deleted_at` timestamp).
  </Accordion>

  <Accordion title="Hard delete is idempotent">
    Hard-deleting a non-existent observation fails with "observation not found".
  </Accordion>
</AccordionGroup>

## Bulk Deletion

For bulk deletion (not available via MCP), use the CLI or HTTP API:

<Tabs>
  <Tab title="CLI">
    ```bash theme={null}
    # Soft delete all observations from a project
    sqlite3 ~/.engram/engram.db "UPDATE observations SET deleted_at = datetime('now') WHERE project = 'old-project'"

    # Hard delete all soft-deleted observations
    sqlite3 ~/.engram/engram.db "DELETE FROM observations WHERE deleted_at IS NOT NULL"
    ```
  </Tab>

  <Tab title="HTTP API">
    ```bash theme={null}
    # Delete observation by ID
    curl -X DELETE http://localhost:7437/api/observations/42

    # Hard delete
    curl -X DELETE http://localhost:7437/api/observations/42?hard=true
    ```
  </Tab>
</Tabs>

## Restoring Soft-Deleted Observations

Soft-deleted observations can be restored manually:

```sql theme={null}
-- Restore observation #42
UPDATE observations SET deleted_at = NULL WHERE id = 42;

-- Restore all soft-deleted observations from a project
UPDATE observations SET deleted_at = NULL WHERE project = 'my-api' AND deleted_at IS NOT NULL;
```

<Info>
  There's no MCP tool for restoring deleted observations — use the SQLite CLI or a database browser.
</Info>

## Privacy Considerations

<Warning>
  Soft deletes keep data on disk. For sensitive information (API keys, credentials, personal data), use **hard delete** or manually purge from the database.
</Warning>

For GDPR compliance or data purging:

1. Hard delete the observation
2. Run `VACUUM` on the database to reclaim space:
   ```bash theme={null}
   sqlite3 ~/.engram/engram.db "VACUUM"
   ```

## Database Size Management

After hard deletes, reclaim disk space:

```bash theme={null}
# Check database size
ls -lh ~/.engram/engram.db

# Reclaim space after hard deletes
sqlite3 ~/.engram/engram.db "VACUUM"
```

<Tip>
  `VACUUM` rebuilds the database file, removing unused space. Run it periodically after bulk hard deletes.
</Tip>

## Related Tools

* [`mem_update`](/mcp/mem-update) - Update observations instead of deleting
* [`mem_search`](/mcp/mem-search) - Find observations to delete
* [`mem_get_observation`](/mcp/mem-get-observation) - View observation before deleting
