pub struct Database { /* private fields */ }Expand description
Database instance managing collections and storage.
§Lifecycle
Database::open() automatically loads all previously created collections from disk.
There is no need to call load_collections() separately.
§Extension (Premium)
Use Database::open_with_observer to inject a DatabaseObserver implementation
from velesdb-premium without modifying this crate.
Implementations§
Source§impl Database
impl Database
Sourcepub fn open<P: AsRef<Path>>(path: P) -> Result<Self>
pub fn open<P: AsRef<Path>>(path: P) -> Result<Self>
Opens or creates a database, automatically loading all existing collections.
This replaces the previous open() + load_collections() two-step pattern.
The new open() is a strict auto-load: all config.json directories under
path are loaded on startup.
§Errors
Returns an error if the directory cannot be created or accessed.
Sourcepub fn open_with_observer<P: AsRef<Path>>(
path: P,
observer: Arc<dyn DatabaseObserver>,
) -> Result<Self>
pub fn open_with_observer<P: AsRef<Path>>( path: P, observer: Arc<dyn DatabaseObserver>, ) -> Result<Self>
Opens a database with a DatabaseObserver (used by velesdb-premium).
The observer receives lifecycle hooks for every collection operation, enabling RBAC, audit logging, multi-tenant routing, etc.
§Errors
Returns an error if the directory cannot be created or accessed.
Sourcepub fn create_collection(
&self,
name: &str,
dimension: usize,
metric: DistanceMetric,
) -> Result<()>
pub fn create_collection( &self, name: &str, dimension: usize, metric: DistanceMetric, ) -> Result<()>
Creates a new collection with the specified parameters.
§Arguments
name- Unique name for the collectiondimension- Vector dimension (e.g., 768 for many embedding models)metric- Distance metric to use for similarity calculations
§Errors
Returns an error if a collection with the same name already exists.
Sourcepub fn create_collection_with_options(
&self,
name: &str,
dimension: usize,
metric: DistanceMetric,
storage_mode: StorageMode,
) -> Result<()>
pub fn create_collection_with_options( &self, name: &str, dimension: usize, metric: DistanceMetric, storage_mode: StorageMode, ) -> Result<()>
Sourcepub fn schema_version(&self) -> u64
pub fn schema_version(&self) -> u64
Returns the current DDL schema version counter.
Sourcepub fn plan_cache(&self) -> &CompiledPlanCache
pub fn plan_cache(&self) -> &CompiledPlanCache
Returns a reference to the compiled query plan cache.
Sourcepub fn collection_write_generation(&self, name: &str) -> Option<u64>
pub fn collection_write_generation(&self, name: &str) -> Option<u64>
Returns the write generation for a named collection, if it exists.
Checks the legacy registry first (covers all collection types).
Sourcepub fn get_collection(&self, name: &str) -> Option<Collection>
pub fn get_collection(&self, name: &str) -> Option<Collection>
Sourcepub fn analyze_collection(&self, name: &str) -> Result<CollectionStats>
pub fn analyze_collection(&self, name: &str) -> Result<CollectionStats>
Analyzes a collection, caches stats, and persists them to disk.
§Errors
Returns an error if the collection does not exist, analysis fails, or stats cannot be serialized and written to disk.
Sourcepub fn get_collection_stats(
&self,
name: &str,
) -> Result<Option<CollectionStats>>
pub fn get_collection_stats( &self, name: &str, ) -> Result<Option<CollectionStats>>
Returns cached statistics when available, loading from disk if present.
§Errors
Returns an error if the on-disk stats file exists but cannot be read or deserialized.
Sourcepub fn build_plan_key(&self, query: &Query) -> PlanKey
pub fn build_plan_key(&self, query: &Query) -> PlanKey
Builds a deterministic cache key for a query (CACHE-02).
Serialises the query to canonical JSON (object keys sorted recursively),
reads the current schema_version, and gathers per-collection
write_generation counters (sorted by collection name) to form a
PlanKey.
§Why canonical JSON instead of Debug
format!("{query:?}") is non-deterministic when the Query AST
contains HashMap-backed fields (FusionConfig::params,
TrainStatement::params) because HashMap iteration order is not
guaranteed across invocations. Canonical JSON with sorted object keys
is stable and produces the same byte sequence for logically identical
queries.
Sourcepub fn explain_query(&self, query: &Query) -> Result<QueryPlan>
pub fn explain_query(&self, query: &Query) -> Result<QueryPlan>
Returns the query plan for a query, with cache status populated (CACHE-02).
If the plan is cached, returns it with cache_hit: Some(true) and
plan_reuse_count set. Otherwise generates a fresh plan with
cache_hit: Some(false).
§Design decision: explain_query does not populate the cache
explain_query intentionally does not insert a new plan into the
compiled plan cache. EXPLAIN is a diagnostic operation; allowing it to
influence cache state would make cache metrics (hit/miss ratios,
plan_reuse_count) unreliable because EXPLAIN calls would be
indistinguishable from real execution hits. Only execute_query is
authorised to write to the cache.
§Errors
Returns an error if the query is invalid.
Sourcepub fn execute_query(
&self,
query: &Query,
params: &HashMap<String, Value>,
) -> Result<Vec<SearchResult>>
pub fn execute_query( &self, query: &Query, params: &HashMap<String, Value>, ) -> Result<Vec<SearchResult>>
Executes a VelesQL query with database-level JOIN resolution.
This method resolves JOIN target collections from the database registry and executes JOIN runtime in sequence. Query plans are cached and reused for identical queries against unchanged collections (CACHE-02).
§Errors
Returns an error if the base collection or any JOIN collection is missing.
Sourcepub fn list_collections(&self) -> Vec<String>
pub fn list_collections(&self) -> Vec<String>
Lists all collection names in the database.
Includes collections created via any typed API (vector, graph, metadata).
Sourcepub fn delete_collection(&self, name: &str) -> Result<()>
pub fn delete_collection(&self, name: &str) -> Result<()>
Deletes a collection by name.
§Arguments
name- Name of the collection to delete
§Errors
Returns an error if the collection does not exist in any registry.
§Concurrency
The existence check and the registry removals are not a single atomic
operation. Under concurrent deletion of the same collection, at most one
caller receives CollectionNotFound; subsequent callers perform no-op
remove() calls which are safe and idempotent. remove_dir_all is
guarded by an exists() check and is therefore also safe.
Sourcepub fn create_vector_collection(
&self,
name: &str,
dimension: usize,
metric: DistanceMetric,
) -> Result<()>
pub fn create_vector_collection( &self, name: &str, dimension: usize, metric: DistanceMetric, ) -> Result<()>
Creates a new vector collection.
§Errors
Returns an error if a collection with the same name already exists.
Sourcepub fn create_vector_collection_with_options(
&self,
name: &str,
dimension: usize,
metric: DistanceMetric,
storage_mode: StorageMode,
) -> Result<()>
pub fn create_vector_collection_with_options( &self, name: &str, dimension: usize, metric: DistanceMetric, storage_mode: StorageMode, ) -> Result<()>
Creates a new vector collection with custom storage options.
§Errors
Returns an error if a collection with the same name already exists.
Sourcepub fn create_graph_collection(
&self,
name: &str,
schema: GraphSchema,
) -> Result<()>
pub fn create_graph_collection( &self, name: &str, schema: GraphSchema, ) -> Result<()>
Creates a new graph collection.
§Errors
Returns an error if a collection with the same name already exists.
Sourcepub fn create_metadata_collection(&self, name: &str) -> Result<()>
pub fn create_metadata_collection(&self, name: &str) -> Result<()>
Creates a new metadata-only collection.
§Errors
Returns an error if a collection with the same name already exists.
Sourcepub fn notify_upsert(&self, collection: &str, point_count: usize)
pub fn notify_upsert(&self, collection: &str, point_count: usize)
Notifies the observer that points were upserted into a collection.
Caller contract: this method is NOT called automatically by
Database internals. HTTP handlers and SDK bindings are responsible
for calling it after a successful upsert, passing the number of points
written. Forgetting to call it means the observer receives no upsert
events for that operation.
No-op when no observer is registered.
Sourcepub fn notify_query(&self, collection: &str, duration_us: u64)
pub fn notify_query(&self, collection: &str, duration_us: u64)
Notifies the observer that a query was executed, with its duration.
Caller contract: this method is NOT called automatically by
Database::execute_query. Callers must measure the wall-clock
duration themselves (e.g. std::time::Instant::now() before the call)
and invoke this method afterwards with the elapsed microseconds.
No-op when no observer is registered.
Sourcepub fn get_vector_collection(&self, name: &str) -> Option<VectorCollection>
pub fn get_vector_collection(&self, name: &str) -> Option<VectorCollection>
Returns a VectorCollection by name.
Checks the typed registry first. If not found there, falls back to
opening the collection directory from disk (e.g. for collections created
via the legacy create_collection API that were not registered in the
typed registry). The opened instance is cached back into the registry
so subsequent calls avoid the disk round-trip.
Returns None if the collection does not exist on disk.
Sourcepub fn get_graph_collection(&self, name: &str) -> Option<GraphCollection>
pub fn get_graph_collection(&self, name: &str) -> Option<GraphCollection>
Returns a GraphCollection by name.
Checks the typed registry first. Falls back to opening from disk if the collection was not registered in-memory (e.g. after a restart or when the collection was auto-created by a graph handler). The instance is cached into the registry so subsequent calls are free.
Returns None if the collection does not exist on disk.
Sourcepub fn get_metadata_collection(&self, name: &str) -> Option<MetadataCollection>
pub fn get_metadata_collection(&self, name: &str) -> Option<MetadataCollection>
Returns a MetadataCollection by name.
Checks the typed registry first. Falls back to opening from disk for collections created before the typed API existed or after a restart. The instance is cached to avoid repeated disk reads.
Returns None if the collection does not exist on disk.
Sourcepub fn create_collection_typed(
&self,
name: &str,
collection_type: &CollectionType,
) -> Result<()>
pub fn create_collection_typed( &self, name: &str, collection_type: &CollectionType, ) -> Result<()>
Creates a new collection with a specific type (Vector or MetadataOnly).
§Arguments
name- Unique name for the collectioncollection_type- Type of collection to create
§Errors
Returns an error if a collection with the same name already exists.
§Examples
use velesdb_core::{Database, CollectionType, DistanceMetric, StorageMode};
let db = Database::open("./data")?;
// Create a metadata-only collection
db.create_collection_typed("products", CollectionType::MetadataOnly)?;
// Create a vector collection
db.create_collection_typed("embeddings", CollectionType::Vector {
dimension: 768,
metric: DistanceMetric::Cosine,
storage_mode: StorageMode::Full,
})?;Sourcepub fn load_collections(&self) -> Result<()>
pub fn load_collections(&self) -> Result<()>
Loads existing collections from disk.
§Deprecation note
This method is called automatically by Database::open.
There is no need to call it manually. It is kept public only for
backward compatibility with code that relied on the old two-step pattern.
§Errors
Returns an error if collection directories cannot be read.
Auto Trait Implementations§
impl !Freeze for Database
impl !RefUnwindSafe for Database
impl Send for Database
impl Sync for Database
impl Unpin for Database
impl UnsafeUnpin for Database
impl !UnwindSafe for Database
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<T> Paint for Twhere
T: ?Sized,
impl<T> Paint for Twhere
T: ?Sized,
Source§fn fg(&self, value: Color) -> Painted<&T>
fn fg(&self, value: Color) -> Painted<&T>
Returns a styled value derived from self with the foreground set to
value.
This method should be used rarely. Instead, prefer to use color-specific
builder methods like red() and
green(), which have the same functionality but are
pithier.
§Example
Set foreground color to white using fg():
use yansi::{Paint, Color};
painted.fg(Color::White);Set foreground color to white using white().
use yansi::Paint;
painted.white();Source§fn bright_black(&self) -> Painted<&T>
fn bright_black(&self) -> Painted<&T>
Source§fn bright_red(&self) -> Painted<&T>
fn bright_red(&self) -> Painted<&T>
Source§fn bright_green(&self) -> Painted<&T>
fn bright_green(&self) -> Painted<&T>
Source§fn bright_yellow(&self) -> Painted<&T>
fn bright_yellow(&self) -> Painted<&T>
Source§fn bright_blue(&self) -> Painted<&T>
fn bright_blue(&self) -> Painted<&T>
Source§fn bright_magenta(&self) -> Painted<&T>
fn bright_magenta(&self) -> Painted<&T>
Source§fn bright_cyan(&self) -> Painted<&T>
fn bright_cyan(&self) -> Painted<&T>
Source§fn bright_white(&self) -> Painted<&T>
fn bright_white(&self) -> Painted<&T>
Source§fn bg(&self, value: Color) -> Painted<&T>
fn bg(&self, value: Color) -> Painted<&T>
Returns a styled value derived from self with the background set to
value.
This method should be used rarely. Instead, prefer to use color-specific
builder methods like on_red() and
on_green(), which have the same functionality but
are pithier.
§Example
Set background color to red using fg():
use yansi::{Paint, Color};
painted.bg(Color::Red);Set background color to red using on_red().
use yansi::Paint;
painted.on_red();Source§fn on_primary(&self) -> Painted<&T>
fn on_primary(&self) -> Painted<&T>
Source§fn on_magenta(&self) -> Painted<&T>
fn on_magenta(&self) -> Painted<&T>
Source§fn on_bright_black(&self) -> Painted<&T>
fn on_bright_black(&self) -> Painted<&T>
Source§fn on_bright_red(&self) -> Painted<&T>
fn on_bright_red(&self) -> Painted<&T>
Source§fn on_bright_green(&self) -> Painted<&T>
fn on_bright_green(&self) -> Painted<&T>
Source§fn on_bright_yellow(&self) -> Painted<&T>
fn on_bright_yellow(&self) -> Painted<&T>
Source§fn on_bright_blue(&self) -> Painted<&T>
fn on_bright_blue(&self) -> Painted<&T>
Source§fn on_bright_magenta(&self) -> Painted<&T>
fn on_bright_magenta(&self) -> Painted<&T>
Source§fn on_bright_cyan(&self) -> Painted<&T>
fn on_bright_cyan(&self) -> Painted<&T>
Source§fn on_bright_white(&self) -> Painted<&T>
fn on_bright_white(&self) -> Painted<&T>
Source§fn attr(&self, value: Attribute) -> Painted<&T>
fn attr(&self, value: Attribute) -> Painted<&T>
Enables the styling Attribute value.
This method should be used rarely. Instead, prefer to use
attribute-specific builder methods like bold() and
underline(), which have the same functionality
but are pithier.
§Example
Make text bold using attr():
use yansi::{Paint, Attribute};
painted.attr(Attribute::Bold);Make text bold using using bold().
use yansi::Paint;
painted.bold();Source§fn rapid_blink(&self) -> Painted<&T>
fn rapid_blink(&self) -> Painted<&T>
Source§fn quirk(&self, value: Quirk) -> Painted<&T>
fn quirk(&self, value: Quirk) -> Painted<&T>
Enables the yansi Quirk value.
This method should be used rarely. Instead, prefer to use quirk-specific
builder methods like mask() and
wrap(), which have the same functionality but are
pithier.
§Example
Enable wrapping using .quirk():
use yansi::{Paint, Quirk};
painted.quirk(Quirk::Wrap);Enable wrapping using wrap().
use yansi::Paint;
painted.wrap();Source§fn clear(&self) -> Painted<&T>
👎Deprecated since 1.0.1: renamed to resetting() due to conflicts with Vec::clear().
The clear() method will be removed in a future release.
fn clear(&self) -> Painted<&T>
resetting() due to conflicts with Vec::clear().
The clear() method will be removed in a future release.Source§fn whenever(&self, value: Condition) -> Painted<&T>
fn whenever(&self, value: Condition) -> Painted<&T>
Conditionally enable styling based on whether the Condition value
applies. Replaces any previous condition.
See the crate level docs for more details.
§Example
Enable styling painted only when both stdout and stderr are TTYs:
use yansi::{Paint, Condition};
painted.red().on_yellow().whenever(Condition::STDOUTERR_ARE_TTY);