// std/memory — append-only durable memory with optional host-backed vector recall.
//
// Import: import "std/memory"
//
// The default backend is deterministic BM25 lexical recall. Call
// `memory_open(namespace, {backend: "vector" | "hybrid", ...})` once to
// switch a namespace to host-provided embeddings via the `memory.embed`
// host capability. Recall queries can override the namespace default per
// call by passing `{mode: "lexical" | "semantic" | "hybrid"}`. Embeddings
// are cached on disk per `(model_hint, content_hash)` so replays are
// deterministic from the recorded event log.
/**
* Configure a memory namespace.
*
* `options.backend` selects the recall backend ("bm25" — default,
* "vector", or "hybrid"). `options.embed_model_hint` selects the host
* embedding model. `options.embed_dim`, `options.bm25_weight`, and
* `options.cosine_weight` are optional. Open events are append-only;
* calling `memory_open` again replaces the active config.
*
* @effects: []
* @errors: []
*/
pub fn memory_open(namespace, options = nil) {
return __memory_open(namespace, options)
}
/**
* Append a memory observation.
*
* Set `options.embed: true` (or open the namespace with backend
* "vector"/"hybrid") to eagerly cache the record's embedding so later
* semantic recall is cache-only.
*
* @effects: []
* @errors: []
*/
pub fn memory_store(namespace, key, value, tags = nil, options = nil) {
return __memory_store(namespace, key, value, tags, options)
}
/**
* Recall active records ranked by the namespace backend.
*
* Pass `options.mode` to override per call ("lexical", "semantic", or
* "hybrid"). `options.embed_model_hint` overrides the namespace embedding
* model for this query only.
*
* @effects: []
* @errors: []
*/
pub fn memory_recall(namespace, query, k = nil, options = nil) {
return __memory_recall(namespace, query, k, options)
}
/**
* memory_summarize.
*
* @effects: []
* @errors: []
*/
pub fn memory_summarize(namespace, window = nil, options = nil) {
return __memory_summarize(namespace, window, options)
}
/**
* memory_forget.
*
* @effects: []
* @errors: []
*/
pub fn memory_forget(namespace, predicate, options = nil) {
return __memory_forget(namespace, predicate, options)
}
/**
* Append an in-place update to the record with `id` and return the updated
* record (or nil if the id is unknown or forgotten).
*
* `patch` may set any of `value`, `tags`, `status`, `scope`, `flags` (a
* `{name: bool}` map merged key-by-key), and `provenance`. Absent keys leave
* the record unchanged; updating `value` refreshes the derived search text.
* The event log stays append-only — the update is overlaid at projection.
*
* @effects: []
* @errors: []
*/
pub fn memory_update(namespace, id, patch, options = nil) {
return __memory_update(namespace, id, patch, options)
}
/**
* Enumerate active records in a namespace, newest first.
*
* Unlike `memory_recall` (query-ranked), this returns the full listing.
* Filter with `options.status`, `options.scope`, `options.tag`, `options.flag`
* (a flag name that must be true), and `options.limit`.
*
* @effects: []
* @errors: []
*/
pub fn memory_list(namespace, options = nil) {
return __memory_list(namespace, options)
}
/**
* Return the active records flagged to auto-surface as reminders — the ones
* whose per-record flag (default `auto_surface`) is true. Deterministic: a
* filtered enumeration, safe to call every turn to build the turn's reminders.
*
* Pass `options.flag` to use a different flag name, plus any `memory_list`
* filter (`status`, `scope`, `tag`, `limit`).
*
* @effects: []
* @errors: []
*/
pub fn memory_reminders(namespace, options = nil) {
let flag = (options ?? {})?.flag ?? "auto_surface"
return memory_list(namespace, (options ?? {}) + {flag: flag})
}