pub struct InMemoryGraph { /* private fields */ }Implementations§
Source§impl InMemoryGraph
impl InMemoryGraph
pub fn new() -> Self
pub fn with_capacity_hint(nodes: usize, relationships: usize) -> Self
pub fn contains_node(&self, node_id: NodeId) -> bool
pub fn contains_relationship(&self, rel_id: RelationshipId) -> bool
Sourcepub fn set_mutation_recorder(
&mut self,
recorder: Option<Arc<dyn MutationRecorder>>,
)
pub fn set_mutation_recorder( &mut self, recorder: Option<Arc<dyn MutationRecorder>>, )
Install (or clear) the mutation recorder. Passing None detaches any
currently-installed recorder. The recorder observes every committed
mutation after it has been applied.
Sourcepub fn mutation_recorder(&self) -> Option<&Arc<dyn MutationRecorder>>
pub fn mutation_recorder(&self) -> Option<&Arc<dyn MutationRecorder>>
Handle to the currently-installed recorder, if any.
Sourcepub fn graph_stats(&self) -> GraphStats
pub fn graph_stats(&self) -> GraphStats
Snapshot of cardinality stats. Cheap: derived from already-tracked
nodes_by_label / relationships_by_type lengths and the active
property-index buckets. The cost model uses this to populate
estimated_rows on plan-tree nodes.
Sourcepub fn memory_estimate(&self) -> MemoryReport
pub fn memory_estimate(&self) -> MemoryReport
Approximate retained-heap breakdown of this graph. See
super::MemoryReport for the methodology and per-component
fields. Intended for benches and the mem_probe* examples;
not on a hot path.
Source§impl InMemoryGraph
impl InMemoryGraph
Sourcepub fn snapshot_payload(&self) -> SnapshotPayload
pub fn snapshot_payload(&self) -> SnapshotPayload
Return the portable graph-state payload. Callers downstream of
lora-store (typically lora-database) feed this into
lora-snapshot for byte-level encoding.
Sourcepub fn load_snapshot_payload(
&mut self,
payload: SnapshotPayload,
) -> Result<SnapshotMeta, SnapshotError>
pub fn load_snapshot_payload( &mut self, payload: SnapshotPayload, ) -> Result<SnapshotMeta, SnapshotError>
Replace the graph from a portable graph-state payload, preserving the currently installed mutation recorder across the swap.
Trait Implementations§
Source§impl BorrowedGraphStorage for InMemoryGraph
impl BorrowedGraphStorage for InMemoryGraph
fn node_ref(&self, id: NodeId) -> Option<&NodeRecord>
fn relationship_ref(&self, id: RelationshipId) -> Option<&RelationshipRecord>
fn node_refs(&self) -> Box<dyn Iterator<Item = &NodeRecord> + '_>
fn node_refs_by_label( &self, label: &str, ) -> Box<dyn Iterator<Item = &NodeRecord> + '_>
fn relationship_refs( &self, ) -> Box<dyn Iterator<Item = &RelationshipRecord> + '_>
fn relationship_refs_by_type( &self, rel_type: &str, ) -> Box<dyn Iterator<Item = &RelationshipRecord> + '_>
Source§impl Clone for InMemoryGraph
impl Clone for InMemoryGraph
Source§impl Debug for InMemoryGraph
impl Debug for InMemoryGraph
Source§impl Default for InMemoryGraph
impl Default for InMemoryGraph
Source§fn default() -> InMemoryGraph
fn default() -> InMemoryGraph
Source§impl GraphStorage for InMemoryGraph
impl GraphStorage for InMemoryGraph
fn list_indexes(&self) -> Vec<IndexDefinition>
fn get_index(&self, name: &str) -> Option<IndexDefinition>
Source§fn fulltext_search(&self, name: &str, query: &str) -> Vec<(u64, f64)>
fn fulltext_search(&self, name: &str, query: &str) -> Vec<(u64, f64)>
(entity_id, score) pairs sorted descending by score. Backends
without fulltext support return an empty vector; the caller is
expected to have validated that the index exists via the
catalog first.Source§fn vector_search(
&self,
name: &str,
query: &LoraVector,
k: usize,
restrict_to: Option<&BTreeSet<u64>>,
) -> Vec<(u64, f64)>
fn vector_search( &self, name: &str, query: &LoraVector, k: usize, restrict_to: Option<&BTreeSet<u64>>, ) -> Vec<(u64, f64)>
(entity_id, score) pairs; the caller sorts by score
descending and truncates to top-k. Backends without vector
support return an empty vector. The caller has already
validated that the index exists via the catalog and that the
query vector matches the configured dimensions. Read moreSource§fn list_constraints(&self) -> Vec<ConstraintDefinition>
fn list_constraints(&self) -> Vec<ConstraintDefinition>
fn get_constraint(&self, name: &str) -> Option<ConstraintDefinition>
Source§fn check_node_create_against_constraints(
&self,
labels: &[String],
properties: &Properties,
) -> Result<(), String>
fn check_node_create_against_constraints( &self, labels: &[String], properties: &Properties, ) -> Result<(), String>
labels and properties violate any registered constraint?
Default returns Ok(()) so backends without a constraint
catalog pay nothing. The in-memory backend overrides this and
the call is virtually free when the catalog is empty.Source§fn check_relationship_create_against_constraints(
&self,
rel_type: &str,
properties: &Properties,
) -> Result<(), String>
fn check_relationship_create_against_constraints( &self, rel_type: &str, properties: &Properties, ) -> Result<(), String>
CREATE ()-[r:TYPE { ... }]->().Source§fn check_node_set_property_against_constraints(
&self,
node_id: NodeId,
key: &str,
value: &PropertyValue,
) -> Result<(), String>
fn check_node_set_property_against_constraints( &self, node_id: NodeId, key: &str, value: &PropertyValue, ) -> Result<(), String>
key = value on this
node violate any registered constraint? Default Ok(()).Source§fn check_node_remove_property_against_constraints(
&self,
node_id: NodeId,
key: &str,
) -> Result<(), String>
fn check_node_remove_property_against_constraints( &self, node_id: NodeId, key: &str, ) -> Result<(), String>
key on this node
violate an existence / key constraint? Default Ok(()).Source§fn check_node_replace_properties_against_constraints(
&self,
node_id: NodeId,
properties: &Properties,
) -> Result<(), String>
fn check_node_replace_properties_against_constraints( &self, node_id: NodeId, properties: &Properties, ) -> Result<(), String>
Ok(()).Source§fn check_relationship_set_property_against_constraints(
&self,
rel_id: RelationshipId,
key: &str,
value: &PropertyValue,
) -> Result<(), String>
fn check_relationship_set_property_against_constraints( &self, rel_id: RelationshipId, key: &str, value: &PropertyValue, ) -> Result<(), String>
fn check_relationship_remove_property_against_constraints( &self, rel_id: RelationshipId, key: &str, ) -> Result<(), String>
Source§fn check_relationship_replace_properties_against_constraints(
&self,
rel_id: RelationshipId,
properties: &Properties,
) -> Result<(), String>
fn check_relationship_replace_properties_against_constraints( &self, rel_id: RelationshipId, properties: &Properties, ) -> Result<(), String>
Ok(()).Source§fn check_node_add_label_against_constraints(
&self,
node_id: NodeId,
label: &str,
) -> Result<(), String>
fn check_node_add_label_against_constraints( &self, node_id: NodeId, label: &str, ) -> Result<(), String>
label to this node
activate a constraint the node currently violates?Source§fn graph_stats(&self) -> GraphStats
fn graph_stats(&self) -> GraphStats
GraphStats::default(),
which the planner treats as “no information available”.Source§fn node_text_candidates(
&self,
label: &str,
property: &str,
query: &str,
) -> Option<Vec<NodeId>>
fn node_text_candidates( &self, label: &str, property: &str, query: &str, ) -> Option<Vec<NodeId>>
Source§fn node_range_candidates(
&self,
label: &str,
property: &str,
lo: Option<&PropertyValue>,
hi: Option<&PropertyValue>,
) -> Option<Vec<NodeId>>
fn node_range_candidates( &self, label: &str, property: &str, lo: Option<&PropertyValue>, hi: Option<&PropertyValue>, ) -> Option<Vec<NodeId>>
[lo, hi] range on label.property.
Both bounds are inclusive at this layer; the caller refilters with
the precise predicate inclusivity (> vs >=, < vs <=). Read moreSource§fn node_point_within_bbox(
&self,
label: &str,
property: &str,
ll: (f64, f64),
ur: (f64, f64),
) -> Option<Vec<NodeId>>
fn node_point_within_bbox( &self, label: &str, property: &str, ll: (f64, f64), ur: (f64, f64), ) -> Option<Vec<NodeId>>
[ll, ur] 2D
bounding box. The executor refilters every id with the precise
predicate, including the z-coordinate when the indexed point
is 3D.Source§fn node_point_within_distance(
&self,
label: &str,
property: &str,
center: (f64, f64),
max_distance: f64,
) -> Option<Vec<NodeId>>
fn node_point_within_distance( &self, label: &str, property: &str, center: (f64, f64), max_distance: f64, ) -> Option<Vec<NodeId>>
max_distance of (x, y). The
candidate set is conservative — the actual great-circle /
cartesian distance check is the executor’s responsibility.Source§fn relationship_text_candidates(
&self,
rel_type: &str,
property: &str,
query: &str,
) -> Option<Vec<RelationshipId>>
fn relationship_text_candidates( &self, rel_type: &str, property: &str, query: &str, ) -> Option<Vec<RelationshipId>>
rel_type whose
property value matches query (substring/prefix/suffix). Mirror
of Self::node_text_candidates for relationship-target indexes.Source§fn relationship_range_candidates(
&self,
rel_type: &str,
property: &str,
lo: Option<&PropertyValue>,
hi: Option<&PropertyValue>,
) -> Option<Vec<RelationshipId>>
fn relationship_range_candidates( &self, rel_type: &str, property: &str, lo: Option<&PropertyValue>, hi: Option<&PropertyValue>, ) -> Option<Vec<RelationshipId>>
rel_type on the
closed [lo, hi] range. Mirror of Self::node_range_candidates.Source§fn relationship_point_within_bbox(
&self,
rel_type: &str,
property: &str,
ll: (f64, f64),
ur: (f64, f64),
) -> Option<Vec<RelationshipId>>
fn relationship_point_within_bbox( &self, rel_type: &str, property: &str, ll: (f64, f64), ur: (f64, f64), ) -> Option<Vec<RelationshipId>>
[ll, ur] 2D bounding
box, scoped to relationships of rel_type. Mirror of
Self::node_point_within_bbox.Source§fn relationship_point_within_distance(
&self,
rel_type: &str,
property: &str,
center: (f64, f64),
max_distance: f64,
) -> Option<Vec<RelationshipId>>
fn relationship_point_within_distance( &self, rel_type: &str, property: &str, center: (f64, f64), max_distance: f64, ) -> Option<Vec<RelationshipId>>
max_distance of (x, y),
scoped to relationships of rel_type. Mirror of
Self::node_point_within_distance.Source§fn contains_node(&self, id: NodeId) -> bool
fn contains_node(&self, id: NodeId) -> bool
Source§fn node(&self, id: NodeId) -> Option<NodeRecord>
fn node(&self, id: NodeId) -> Option<NodeRecord>
BorrowedGraphStorage::node_ref and
override [with_node] to avoid clones on the hot path.Source§fn all_node_ids(&self) -> Vec<NodeId> ⓘ
fn all_node_ids(&self) -> Vec<NodeId> ⓘ
Source§fn node_ids_by_label(&self, label: &str) -> Vec<NodeId> ⓘ
fn node_ids_by_label(&self, label: &str) -> Vec<NodeId> ⓘ
fn contains_relationship(&self, id: RelationshipId) -> bool
fn relationship(&self, id: RelationshipId) -> Option<RelationshipRecord>
fn all_rel_ids(&self) -> Vec<RelationshipId> ⓘ
fn rel_ids_by_type(&self, rel_type: &str) -> Vec<RelationshipId> ⓘ
Source§fn relationship_endpoints(&self, id: RelationshipId) -> Option<(NodeId, NodeId)>
fn relationship_endpoints(&self, id: RelationshipId) -> Option<(NodeId, NodeId)>
(src, dst) for a relationship. Required because
traversal uses it on hot paths; a backend that stores endpoints
alongside the id index can answer this without fetching properties.Source§fn expand_ids(
&self,
node_id: NodeId,
direction: Direction,
types: &[String],
) -> Vec<(RelationshipId, NodeId)>
fn expand_ids( &self, node_id: NodeId, direction: Direction, types: &[String], ) -> Vec<(RelationshipId, NodeId)>
Source§fn try_for_each_expand_id<F, E>(
&self,
node_id: NodeId,
direction: Direction,
types: &[String],
visit: F,
) -> Result<(), E>
fn try_for_each_expand_id<F, E>( &self, node_id: NodeId, direction: Direction, types: &[String], visit: F, ) -> Result<(), E>
(relationship_id, other_node_id) pairs without
forcing backends to allocate an intermediate Vec. The default keeps the
trait easy to implement; hot backends can override it.fn all_labels(&self) -> Vec<String>
fn all_relationship_types(&self) -> Vec<String>
fn with_node<F, R>(&self, id: NodeId, f: F) -> Option<R>
fn with_relationship<F, R>(&self, id: RelationshipId, f: F) -> Option<R>
fn has_node(&self, id: NodeId) -> bool
fn has_relationship(&self, id: RelationshipId) -> bool
fn node_count(&self) -> usize
fn relationship_count(&self) -> usize
fn all_nodes(&self) -> Vec<NodeRecord>
fn nodes_by_label(&self, label: &str) -> Vec<NodeRecord>
fn all_relationships(&self) -> Vec<RelationshipRecord>
fn relationships_by_type(&self, rel_type: &str) -> Vec<RelationshipRecord>
fn relationship_ids_of( &self, node_id: NodeId, direction: Direction, ) -> Vec<RelationshipId> ⓘ
fn outgoing_relationships(&self, node_id: NodeId) -> Vec<RelationshipRecord>
fn incoming_relationships(&self, node_id: NodeId) -> Vec<RelationshipRecord>
fn relationships_of( &self, node_id: NodeId, direction: Direction, ) -> Vec<RelationshipRecord>
fn degree(&self, node_id: NodeId, direction: Direction) -> usize
fn expand( &self, node_id: NodeId, direction: Direction, types: &[String], ) -> Vec<(RelationshipRecord, NodeRecord)>
fn neighbors( &self, node_id: NodeId, direction: Direction, types: &[String], ) -> Vec<NodeRecord>
fn all_node_property_keys(&self) -> Vec<String>
fn all_relationship_property_keys(&self) -> Vec<String>
fn label_property_keys(&self, label: &str) -> Vec<String>
fn rel_type_property_keys(&self, rel_type: &str) -> Vec<String>
fn find_nodes_by_property(
&self,
label: Option<&str>,
key: &str,
value: &PropertyValue,
) -> Vec<NodeRecord>where
Self: Sized,
fn find_node_ids_by_property(
&self,
label: Option<&str>,
key: &str,
value: &PropertyValue,
) -> Vec<NodeId> ⓘwhere
Self: Sized,
fn find_relationships_by_property(
&self,
rel_type: Option<&str>,
key: &str,
value: &PropertyValue,
) -> Vec<RelationshipRecord>where
Self: Sized,
fn find_relationship_ids_by_property(
&self,
rel_type: Option<&str>,
key: &str,
value: &PropertyValue,
) -> Vec<RelationshipId> ⓘwhere
Self: Sized,
fn node_exists_with_label_and_property(
&self,
label: &str,
key: &str,
value: &PropertyValue,
) -> boolwhere
Self: Sized,
fn relationship_exists_with_type_and_property(
&self,
rel_type: &str,
key: &str,
value: &PropertyValue,
) -> boolwhere
Self: Sized,
fn is_isolated(&self, node_id: NodeId) -> bool
fn expand_detailed( &self, node_id: NodeId, direction: Direction, types: &[String], ) -> Vec<ExpandedRelationship>
fn node_has_label(&self, node_id: NodeId, label: &str) -> boolwhere
Self: Sized,
fn node_labels(&self, node_id: NodeId) -> Option<Vec<String>>where
Self: Sized,
fn node_properties(&self, node_id: NodeId) -> Option<Properties>where
Self: Sized,
fn node_property(&self, node_id: NodeId, key: &str) -> Option<PropertyValue>where
Self: Sized,
fn relationship_type(&self, rel_id: RelationshipId) -> Option<String>where
Self: Sized,
fn relationship_properties(&self, rel_id: RelationshipId) -> Option<Properties>where
Self: Sized,
fn relationship_property(
&self,
rel_id: RelationshipId,
key: &str,
) -> Option<PropertyValue>where
Self: Sized,
fn relationship_source(&self, rel_id: RelationshipId) -> Option<NodeId>
fn relationship_target(&self, rel_id: RelationshipId) -> Option<NodeId>
fn other_node(&self, rel_id: RelationshipId, node_id: NodeId) -> Option<NodeId>
fn has_label_name(&self, label: &str) -> bool
fn has_relationship_type_name(&self, rel_type: &str) -> bool
fn all_property_keys(&self) -> Vec<String>where
Self: Sized,
fn has_property_key(&self, key: &str) -> boolwhere
Self: Sized,
fn label_has_property_key(&self, label: &str, key: &str) -> boolwhere
Self: Sized,
fn rel_type_has_property_key(&self, rel_type: &str, key: &str) -> boolwhere
Self: Sized,
Source§impl GraphStorageMut for InMemoryGraph
impl GraphStorageMut for InMemoryGraph
fn try_create_node( &mut self, labels: Vec<String>, properties: Properties, ) -> Option<NodeRecord>
fn create_relationship( &mut self, src: NodeId, dst: NodeId, rel_type: &str, properties: Properties, ) -> Option<RelationshipRecord>
fn set_node_property( &mut self, node_id: NodeId, key: String, value: PropertyValue, ) -> bool
fn remove_node_property(&mut self, node_id: NodeId, key: &str) -> bool
fn add_node_label(&mut self, node_id: NodeId, label: &str) -> bool
fn remove_node_label(&mut self, node_id: NodeId, label: &str) -> bool
fn set_relationship_property( &mut self, rel_id: RelationshipId, key: String, value: PropertyValue, ) -> bool
fn remove_relationship_property( &mut self, rel_id: RelationshipId, key: &str, ) -> bool
fn delete_relationship(&mut self, rel_id: RelationshipId) -> bool
Source§fn delete_node(&mut self, node_id: NodeId) -> bool
fn delete_node(&mut self, node_id: NodeId) -> bool
Source§fn detach_delete_node(&mut self, node_id: NodeId) -> bool
fn detach_delete_node(&mut self, node_id: NodeId) -> bool
Source§fn clear(&mut self)
fn clear(&mut self)
Source§fn create_index(
&mut self,
request: IndexRequest,
if_not_exists: bool,
) -> Result<CreateIndexOutcome, CreateIndexError>
fn create_index( &mut self, request: IndexRequest, if_not_exists: bool, ) -> Result<CreateIndexOutcome, CreateIndexError>
CreateIndexError::Unsupported. Read moreSource§fn drop_index(
&mut self,
name: &str,
if_exists: bool,
) -> Result<DropIndexOutcome, DropIndexError>
fn drop_index( &mut self, name: &str, if_exists: bool, ) -> Result<DropIndexOutcome, DropIndexError>
DropIndexError::Unsupported.
if_exists collapses missing-index errors into
DropIndexOutcome::NoOpMissing.Source§fn create_constraint(
&mut self,
request: ConstraintRequest,
if_not_exists: bool,
) -> Result<CreateConstraintOutcome, CreateConstraintError>
fn create_constraint( &mut self, request: ConstraintRequest, if_not_exists: bool, ) -> Result<CreateConstraintOutcome, CreateConstraintError>
CreateConstraintError::Unsupported.
Uniqueness/key kinds may transparently register a backing range
index of the same name.Source§fn drop_constraint(
&mut self,
name: &str,
if_exists: bool,
) -> Result<DropConstraintOutcome, DropConstraintError>
fn drop_constraint( &mut self, name: &str, if_exists: bool, ) -> Result<DropConstraintOutcome, DropConstraintError>
Source§fn create_node(
&mut self,
labels: Vec<String>,
properties: Properties,
) -> NodeRecordwhere
Self: Sized,
fn create_node(
&mut self,
labels: Vec<String>,
properties: Properties,
) -> NodeRecordwhere
Self: Sized,
Self::try_create_node so allocation/id exhaustion can surface as
an ordinary error instead of a process panic.