# Remember a fact

> Store one fact so the agent can recall it later by meaning. The text is embedded on write; retrieval is semantic, not keyword.

`POST https://api.zavu.dev/v1/memory`

Store one fact so the agent can recall it later by meaning. The text is embedded on write; retrieval is semantic, not keyword.

**Scope goes in the body here.** Pass `scope` plus the matching `contactId` / `conversationId`. Omit it for the project scope. Every read endpoint takes the scope as a `?scope=` query parameter instead — see the `scope` parameter on `GET /v1/memory`.

**One fact per call.** A paragraph carrying five unrelated facts is embedded as an average of all five and retrieved well by none of them.

## Body

- `text` (string, required): What to remember. Max 8,192 bytes of UTF-8. Write one fact per call: a paragraph holding five unrelated facts embeds as an average of all five and is retrieved well by none of them.
- `scope` (string): Which namespace a memory belongs to. Scopes are isolated: a search in one never returns a memory from another. - `project`: shared by the whole project. What the agent knows in general. - `contact`: what the agent knows about one person, across every conversation with them. - `conversation`: what the agent knows about one inbox thread. Defaults to `project` everywhere. `contact` and `conversation` require the matching id. One of: `project`, `contact`, `conversation`.
- `contactId` (string): Required when `scope` is `contact`.
- `conversationId` (string): Required when `scope` is `conversation`.
- `metadata` (object): Arbitrary string tags stored alongside the fact and returned with it. Keys max 64 chars, values max 512, whole object max 2,048 bytes. Not searchable — search matches `text` only.
  - `{key}` (string)
- `ttlSeconds` (integer): Delete the fact after this many seconds. 60 to 63,072,000 (2 years). Omit to keep it until deleted.

## Responses

### 201

Fact stored.

- `memory` (object, required): A stored fact, as returned when it is created.
  - `id` (string, required)
  - `scope` (string, required): Which namespace a memory belongs to. Scopes are isolated: a search in one never returns a memory from another. - `project`: shared by the whole project. What the agent knows in general. - `contact`: what the agent knows about one person, across every conversation with them. - `conversation`: what the agent knows about one inbox thread. Defaults to `project` everywhere. `contact` and `conversation` require the matching id. One of: `project`, `contact`, `conversation`.
  - `createdAt` (string<date-time>, required)
  - `expiresAt` (string<date-time>): When the fact self-deletes. Present only when it was stored with `ttlSeconds`, or when the key is a test-mode key (forced to 30 days).

### 400

Invalid body, oversized text, or a scope without its id.

- `code` (string, required)
- `message` (string, required)
- `details` (object)

### 401

Unauthorized.

- `code` (string, required)
- `message` (string, required)
- `details` (object)

### 429

A quota is exhausted. `memory_scope_full` means this scope is at its cap (10,000 facts for project, 2,000 per contact, 1,000 per conversation); `memory_limit_exceeded` means the plan's monthly unit quota is spent. Reads and deletes keep working in both cases.

- `code` (string, required)
- `message` (string, required)
- `details` (object)

### 503

Memory is not available for this deployment.

- `code` (string, required)
- `message` (string, required)
- `details` (object)

## Example

```bash
curl -X POST "https://api.zavu.dev/v1/memory" \
  -H "Authorization: Bearer $ZAVUDEV_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "text": "Orders placed before 2pm ship the same day."
}'
```

```typescript
import Zavudev from "@zavudev/sdk";

const zavu = new Zavudev({ apiKey: process.env.ZAVUDEV_API_KEY });

const result = await zavu.memory.add({
  text: "Orders placed before 2pm ship the same day.",
});

console.log(result);
```
