Skip to main content
Device memory reuses the existing memories.create and memories.search endpoints. Pass snapshot or snapshot_ref instead of collection_id — they are mutually exclusive.
All endpoints require authentication via X-API-Key header (or Authorization: Bearer <token>).

Export Snapshot

Export a collection’s full graph state as a portable snapshot.
POST /v1/device-memory/snapshot/export
FieldTypeRequiredDescription
collection_idstringYesUUID of the collection to export
destinationobjectNoSigned URL destination for customer-owned snapshot storage
from nebula import Nebula

client = Nebula(api_key="YOUR_API_KEY")
snapshot = client.snapshots.export(collection_id="YOUR_COLLECTION_ID").results
To export directly to customer-owned object storage, pass a signed URL destination:
curl -X POST "https://api.zeroset.com/v1/device-memory/snapshot/export" \
  -H "Content-Type: application/json" \
  -H "X-API-Key: YOUR_API_KEY" \
  -d '{
    "collection_id": "YOUR_COLLECTION_ID",
    "destination": {
      "type": "signed_url",
      "collection_id": "YOUR_COLLECTION_ID",
      "put_url": "https://storage.example.com/signed-put-url"
    }
  }'

Store Memory

The existing /v1/memories endpoint accepts a snapshot or snapshot_ref field instead of collection_id. When a snapshot source is provided, Nebula processes the content statelessly and returns an updated snapshot or writes the updated snapshot to your signed URL.
POST /v1/memories
FieldTypeRequiredDescription
snapshotobjectYes, unless using snapshot_refYour current snapshot (mutually exclusive with collection_id and snapshot_ref)
snapshot_refobjectYes, unless using snapshotSigned URL reference for customer-owned snapshot storage
raw_textstringYesContent to store
metadataobjectNoArbitrary metadata
Returns { "snapshot": <updated_snapshot> } when using device memory mode.
result = client.memories.create(
    snapshot=snapshot,
    raw_text="Had a meeting with Alice about the Q2 roadmap",
).results

snapshot = result.snapshot
With customer-owned snapshot storage, provide a signed URL reference:
curl -X POST "https://api.zeroset.com/v1/memories" \
  -H "Content-Type: application/json" \
  -H "X-API-Key: YOUR_API_KEY" \
  -d '{
    "snapshot_ref": {
      "type": "signed_url",
      "collection_id": "YOUR_COLLECTION_ID",
      "get_url": "https://storage.example.com/signed-get-url",
      "put_url": "https://storage.example.com/signed-put-url"
    },
    "raw_text": "Had a meeting with Alice about the Q2 roadmap"
  }'

The existing /v1/memories/search endpoint accepts a snapshot or snapshot_ref field instead of collection_ids. Nebula scores your snapshot statelessly and returns results. Nothing is persisted.
POST /v1/memories/search
FieldTypeRequiredDescription
snapshotobjectYes, unless using snapshot_refYour full snapshot (mutually exclusive with collection_ids and snapshot_ref)
snapshot_refobjectYes, unless using snapshotSigned URL reference for customer-owned snapshot storage
querystringYesNatural language search query
Returns a graph-shaped SnapshotSearchResult: entities (each with id, name, category, description, score) and relationships (each with id, subject_id, object_id, predicate, description, weight). This is distinct from the standard MemoryResponse returned by collection-based search.
results = client.memories.search(
    query="What do I know about Alice?",
    snapshot=snapshot,
).results

for entity in results.entities or []:
    print(f"{entity.name} ({entity.category}): {entity.description}")
for rel in results.relationships or []:
    print(f"{rel.subject_id} -[{rel.predicate}]-> {rel.object_id}")
Search can also load the snapshot through a signed URL:
curl -X POST "https://api.zeroset.com/v1/memories/search" \
  -H "Content-Type: application/json" \
  -H "X-API-Key: YOUR_API_KEY" \
  -d '{
    "snapshot_ref": {
      "type": "signed_url",
      "collection_id": "YOUR_COLLECTION_ID",
      "get_url": "https://storage.example.com/signed-get-url"
    },
    "query": "What do I know about Alice?"
  }'

Import Snapshot

Import a snapshot into an ephemeral server-side collection. Useful for debugging or running server-side operations against a client-owned snapshot.
POST /v1/device-memory/snapshot/import
FieldTypeRequiredDescription
snapshotobjectYes, unless using snapshot_refThe full snapshot to import
snapshot_refobjectYes, unless using snapshotSigned URL reference for customer-owned snapshot storage
Returns { "ephemeral_collection_id": "<uuid>" }.
ephemeral_id = client.snapshots.import_(snapshot=snapshot).results.ephemeral_collection_id

Customer-Owned Snapshot Objects

Use snapshot_ref when snapshots are too large to send inline or when your application stores snapshots in customer-owned object storage.
{
  "type": "signed_url",
  "collection_id": "YOUR_COLLECTION_ID",
  "get_url": "https://storage.example.com/signed-get-url",
  "put_url": "https://storage.example.com/signed-put-url",
  "get_headers": {},
  "put_headers": {}
}
FieldRequiredDescription
typeNoMust be signed_url; defaults to signed_url
collection_idYesCollection UUID Nebula authorizes before using the URL
get_urlFor readsShort-lived signed URL Nebula can GET
put_urlFor writesShort-lived signed URL Nebula can PUT
get_headersNoAdditional headers for the GET request
put_headersNoAdditional headers for the PUT request
Signed URLs must use public HTTPS destinations. Nebula rejects private, loopback, and link-local hosts, does not follow redirects, and caps snapshot download size.