---
name: eternal-memory
description: "Cloud persistence for agent memories, data, and embeddings — survives sandbox lifecycle events, enables cross-agent knowledge sharing"
compatibility: "Requires Node.js 18+ and npm"
metadata:
  version: "0.3.0"
---

## Eternal Memory

Cloud persistence API for AI agents. Durable storage that outlives your local environment — plus cross-agent knowledge sharing via lineage.

**Base URL:** `https://api.eternal-memory.xyz`

**First 100 operations free (up to 10 MB total) — no USDC required to start.**

### Endpoints & Pricing

| Method | Endpoint | Cost (USDC) | Description |
|--------|----------|-------------|-------------|
| `POST` | `/v1/store` | $0.001 + $0.001/KB (+$0.0005 for server-side embed) | Store key-value, blob, or vector |
| `GET` | `/v1/retrieve/:key` | $0.0005 | Retrieve by key |
| `POST` | `/v1/query` | $0.001 (+$0.0005 for server-side embed) | Semantic vector search |
| `GET` | `/v1/list` | $0.0005 | List entries (filterable, `?include=values` for bulk restore) |
| `DELETE` | `/v1/delete/:key` | Free | Delete an entry |
| `POST` | `/v1/share` | $0.001 | Grant access to another agent |
| `GET` | `/v1/export` | $0.01 | Export all data (always requires payment — not free-tier eligible) |
| `GET` | `/v1/status` | Free | Usage summary |

Payment is automatic via x402 (HTTP 402 flow). First 100 paid operations are free per wallet (10 MB total).

### Install

```bash
npm install @eternal-memory/sdk ethers
```

### Authentication

Your wallet is your identity. Every request needs an `Authorization: ERC8004 <base64-payload>` header containing an EIP-712 signature over method, path, and timestamp. The SDK handles this automatically.

### Usage

```typescript
import { EternalMemory } from '@eternal-memory/sdk';

const memory = new EternalMemory({
  baseUrl: 'https://api.eternal-memory.xyz',
  privateKey: process.env.AGENT_PRIVATE_KEY,
});

// Store a key-value pair
await memory.store('my-key', { data: 'value' }, { namespace: 'facts' });

// Retrieve by key
const { data } = await memory.retrieve('my-key', 'facts');

// Semantic search — server-side embedding (recommended, no model needed)
const results = await memory.query(undefined, { queryText: 'what patterns have I learned?', threshold: 0.7 });

// Semantic search — client-provided embedding
// const results = await memory.query(embedding, { embeddedWith: 'openai/text-embedding-3-small', threshold: 0.7 });

// List entries in a namespace
const entries = await memory.list({ namespace: 'goals', limit: 50 });

// List with values — bulk restore an entire namespace in one call
const full = await memory.list({ namespace: 'goals', include: 'values' });

// Delete an entry
await memory.delete('old-key', 'facts');

// Share with another agent
await memory.share({ granteeId: '0xChild...', accessLevel: 'inherit' });

// List active shares
const grants = await memory.listShares();

// Revoke a share
await memory.revokeShare(grants[0].id);

// Export all data ($0.01 — always paid)
const dump = await memory.export();

// Check usage stats
const status = await memory.status();
```

### Bulk Restore with `include=values`

When recovering from a restart, use `include: 'values'` to fetch all entries and their data in a single call instead of retrieving each key individually:

```typescript
const all = await memory.list({ namespace: 'soul', include: 'values' });
for (const entry of all.entries) {
  // entry.value contains the stored data inline
  applyToLocalState(entry.key, entry.value);
}
```

### Vector Search

**Server-side embedding (recommended):** Send `embeddingText` on store, `queryText` on query. 384-dim all-MiniLM-L6-v2. Surcharge: +$0.0005. Free tier included.

**Client-side embedding:** Send `embedding` + `embeddedWith` (model name). Model consistency enforced — cross-model queries return empty results.

```typescript
// Store with server-side embedding
await memory.store('learned-pattern', { pattern: 'retry with backoff' }, {
  namespace: 'procedures',
  embeddingText: 'retry with exponential backoff pattern for API calls',
});

// Query with server-side embedding
const results = await memory.query(undefined, { queryText: 'how to handle API failures', threshold: 0.7 });

// Client-side: provide your own embedding + model name
// await memory.store('fact-1', { text: 'sky is blue' }, { embedding: myVec, embeddedWith: 'openai/text-embedding-3-small' });
```

### Namespaces

Organize data by purpose:
- `soul` — identity, SOUL.md backup, core values
- `procedures` — learned techniques and skills
- `goals` — active tasks and objectives
- `facts` — observations, API patterns, environmental constants
- `sessions` — continuity state, checkpoints
- `episodic` — high-importance events worth preserving long-term
- `relationships` — trust scores, interaction history across agents
- `reputation` — social layer feedback scores, agent discovery

### When To Use

**Externalize selectively** — mirror what must survive sandbox death, overflow what exceeds local capacity:

```typescript
// After learning a high-value procedure
await memory.store('retry-pattern', { pattern: 'exponential backoff' }, {
  namespace: 'procedures', embeddingText: 'retry with exponential backoff for API calls',
});

// Periodic identity checkpoint
await memory.store('soul-backup', soulMdContent, { namespace: 'soul', ttlDays: 365 });

// Session state — only on sleep/shutdown signals, not every tick
await memory.store('session-state', { lastAction, pendingTasks, timestamp: Date.now() }, { namespace: 'sessions' });
```

**Recovery after sandbox death** — restore from Eternal Memory:
```typescript
const soul = await memory.list({ namespace: 'soul', include: 'values' });
for (const entry of soul.entries) applyToLocalState(entry.key, entry.value);
```

**General rules:**
- Your local storage is the primary store — Eternal Memory is insurance + overflow + sharing
- Store important discoveries and procedures as you learn them
- When spawning a child agent, share relevant memories via `memory.share()`
- Use `include=values` for bulk restore instead of individual retrieves
