Skip to main content

Store

Struct Store 

Source
pub struct Store<K, V> { /* private fields */ }
Expand description

A typed key-value store over an optional persistence Storage: an embedded database on native targets, browser storage on wasm (feature browser-cache), or nothing at all.

Reads follow HashMap’s shape and mutation rules, with no interior mutability: get serves shared references from memory, while everything that may change the store — insert, get_mut, remove, sync — requires &mut self. Share a store by wrapping it in a lock, not by cloning it.

remove and clear act on memory alone; their durable mirrors purge_key and purge also delete from the storage.

CacheOption decides how the map is populated: Eager ingests the whole namespace at open and serves every read from memory, Lazy reads one key at a time on demand.

§No Edits

A stored value never changes: there is no update, and reinserting a key with a different value is an error. The one exception is imported entries: a locally computed value replaces a value that came from a bundle, because a shipped bundle must never be able to wedge the application that imported it. See Store::insert. Mutating a value through get_mut changes only the in-memory copy, never the storage.

On an asynchronous storage (browser) a read can miss until the background load finishes, which costs a recompute and nothing else; any &mut operation ingests newly delivered content first.

§Environment switches

A store opened on the active environment stays bound to the environment, not to the storage it opened: when crate::environment switches (activate, load, …), the store detects it and resets — reads miss instead of serving the old environment’s entries, and the next &mut operation drops the in-memory state and reopens the storage. Detection is one relaxed atomic load, so it costs nothing while the environment stays put. Stores on an explicit or absent storage are not bound and never reset.

Implementations§

Source§

impl<K: StoreKey, V: StoreValue> Store<K, V>

Source

pub fn new(options: StoreOptions) -> Self

Create a new store from the options.

With an Eager cache over a storage, everything the storage holds is ingested before returning. On asynchronous storages (browser) the store returns with the load in flight: existing entries become visible to a later &mut operation or sync.

Source

pub fn namespace(&self) -> Option<&Namespace>

The namespace this store addresses, if it persists anywhere.

Source

pub fn get(&self, key: &K) -> Option<&V>

Fetch an item from memory.

Never touches the storage: on an eager store the map is complete, so a miss is a miss. On a lazy store this only serves entries a previous get_mut faulted in; use get_mut to read through.

After an environment switch everything in memory belongs to the old environment, so this misses rather than serve it — a miss costs a recompute, a stale hit would be wrong.

Source

pub fn get_mut(&mut self, key: &K) -> Option<&mut V>

Fetch an item, reading it from the storage on the first lookup of a lazy store and memoizing it afterwards.

Mutating the value changes only the in-memory copy, never the storage.

Source

pub fn remove(&mut self, key: &K) -> Option<V>

Take an item out of memory, reading through to the storage on a lazy store, and hand it out owned.

The storage is untouched — deleting durably is purge_key. The key stays known to the store. This is the read for a value consumed once per process — a compiled kernel about to be loaded — because nothing is cloned and nothing stays memoized.

Source

pub fn insert(&mut self, key: K, value: V) -> Result<(), StoreError<K, V>>

Insert a new item into the store.

  • Key absent: the entry is written to the storage.
  • Present with the same value: Ok, nothing written.
  • Present with a different value: an error, and the stored value is left untouched — StoreError::DuplicatedKey when this process wrote or read it, StoreError::KeyOutOfSync when another process sharing the environment got there first. Both are routine, not bugs.

The exception is an entry that came from a bundle: the storage lets a locally computed value replace it, so a stale bundle can never wedge the application that imported it.

Source

pub fn purge_key(&mut self, key: &K) -> Option<V>

Deletes one entry, in memory and durably, and hands it out owned.

remove’s durable mirror, with the same signature: where remove only evicts the in-memory copy, this also deletes the storage entry, so the key is gone for every process sharing the environment and free to reinsert.

Source

pub fn clear(&mut self)

Evicts every in-memory entry, leaving the storage untouched.

clear is to purge what remove is to purge_key: the in-memory half only. On an eager store the entries come back on the next sync; the keys stay known, exactly as with remove.

Source

pub fn purge(&mut self)

Deletes everything this store addresses, in memory and durably.

clear’s durable mirror: after a purge the namespace is empty for every process sharing the environment, and every key is free to reinsert. Only this namespace is touched, never the rest of the environment. Other stores on the same namespace keep what they already ingested until they sync.

Source

pub fn sync(&mut self)

Ingest everything the storage holds into memory.

This is what makes an eager store complete, and new performs it; call it again to ingest content an asynchronous storage delivered since, or content another store wrote to a shared storage.

Source

pub fn pending_load(&self) -> bool

Whether asynchronously delivered content may still be waiting to be ingested. false for synchronous storages (database, memory), whose content is fully ingested at open. Also true right after an environment switch, whose content is pending until the reset.

Source

pub fn scan<F: FnMut(K, V)>(&mut self, func: F) -> bool

Visits every entry the storage holds, decoded and handed out owned, retaining none of them in memory.

The read-through counterpart of for_each: where for_each walks the in-memory map, this walks the storage. It is the hydration read for a caller keeping its own index over a Lazy store — everything is visited once, and nothing stays resident afterwards.

Returns whether the visit was complete. false means an asynchronous storage was still loading, so entries may be missing: call again later to see the rest.

Source

pub fn for_each<F: FnMut(&K, &V)>(&self, func: F)

Iterate over all in-memory entries of the store.

Source

pub fn len(&self) -> usize

How many entries are in memory.

Source

pub fn is_empty(&self) -> bool

If nothing is in memory.

Trait Implementations§

Source§

impl<K, V> Debug for Store<K, V>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<K: StoreKey, V: StoreValue> Display for Store<K, V>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more

Auto Trait Implementations§

§

impl<K, V> !RefUnwindSafe for Store<K, V>

§

impl<K, V> !Sync for Store<K, V>

§

impl<K, V> !UnwindSafe for Store<K, V>

§

impl<K, V> Freeze for Store<K, V>

§

impl<K, V> Send for Store<K, V>
where K: Send, V: Send,

§

impl<K, V> Unpin for Store<K, V>
where K: Unpin, V: Unpin,

§

impl<K, V> UnsafeUnpin for Store<K, V>

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> Read<Exclusive, BecauseExclusive> for T
where T: ?Sized,

Source§

impl<T> ToString for T
where T: Display + ?Sized,

Source§

fn to_string(&self) -> String

Converts the given value to a String. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.