Summary#
Memory.Remember(file, about: record) reads a stored file's text, splits it up, and adds it to the app's searchable
memory as memory about that record — so Memory.Search can answer from a document the way it answers from a
[Searchable] field. Memory.Forget(file) takes it back out. Both are available under using Osyrin.Memory;.
Signature#
using Osyrin.Memory;
using Osyrin.Storage;
bool Memory.Remember(
FileAsset file, // the stored file whose text to index
Entity about) // the record this file is about — its memory is found through that record
int Memory.Forget(FileAsset file) // how many memory entries were removedDescription#
Storing a file and remembering it are two different acts, and this verb is the second one. An app can hold attachments it never wants answered from — a signed copy, a scan kept for the record — and uploading is not a decision about recall. So nothing is indexed until someone asks for it.
about: is what makes it findable at all#
Memory is reached through the record it belongs to: you can find a file's text exactly when you can read the record
it was filed against. That is the whole of its access control, and it is why about: is required rather than
inferred. A file remembered about nothing would be memory nobody could ever read.
Filing the same file against a different record is a different claim, and you make it by calling the verb again with that record.
It records who asked#
Whoever calls Memory.Remember is the author of the memory it creates, so Memory.Search(by: someone) can
answer "what did they put in front of us", and origin: tells a document somebody filed apart from text that simply
followed the data. Because that authorship is the point, the call refuses when nobody is authenticated rather
than storing entries that claim to have appeared on their own.
The work is queued, not awaited#
Reading a document, splitting it and embedding it is real work, so Memory.Remember returns once the work is
queued — true when it was, false when this host has no worker to do it. The file becomes searchable shortly
afterwards. Remembering the same file twice is safe: the second call replaces that file's entries rather than
adding a second copy, which is also how a re-uploaded file stops answering with its old text.
Forgetting#
Memory.Forget(file) removes the file's entries from memory and returns how many there were, so "forgot it" and
"there was nothing to forget" are distinguishable without a second query. The file itself is untouched —
forgetting is about recall, not storage. A file you still hold is not a file you must still be answering from.
Examples#
using Osyrin.Memory;
using Osyrin.Storage;
entity Order {
[MaxLength(80)] string Reference;
[Searchable(Memory)] string Notes;
}
bool Keep(Order o, FileAsset contract) {
// from now on, searching this order can answer from the contract's text
return Memory.Remember(contract, about: o);
}using Osyrin.Memory;
using Osyrin.Storage;
int Drop(FileAsset contract) {
return Memory.Forget(contract); // the file stays; only its memory goes
}See also#
- using Memory (semantic search) — asking questions of what you remembered, and
by:/origin:for who filed it - [Searchable] — the other way text gets into memory: a
[Searchable]field, kept in sync for you - Memory.Link / Memory.Unlink — stating why two records are related, in words search can find