digraph StorageWorkflow {
fontname = "Helvetica,Arial,sans-serif"
layout = dot
rankdir = LR
ranksep = 0.9;
nodesep = 0.7;
splines = true;
compound = true;
bgcolor = "white"
node [
fontname = "Helvetica,Arial,sans-serif",
shape = box,
style = "filled,rounded",
color = "#555555",
fillcolor = "white",
penwidth = 1.5
]
edge [
fontname = "Helvetica,Arial,sans-serif",
color = "#333333",
fontsize = 9,
fontcolor = "#555555",
labeldistance = 2.0,
penwidth = 1.2
]
subgraph cluster_inputs {
label = "Inputs"
style = "dashed"
color = "#888888"
fontcolor = "#555555"
margin = 18
schema [label = <
| Schema |
| • relation name |
| • arity (column count) |
>, fillcolor = "#E8F4FD", color = "#2196F3"]
row_data [label = <
| Row Data |
| • Vec<Value> |
| • Int / Str / Id(RowId) |
>, fillcolor = "#E8F4FD", color = "#2196F3"]
}
subgraph cluster_setup {
label = "Setup (open backend, declare relations)"
style = "dashed"
color = "#9C27B0"
fontcolor = "#7B1FA2"
margin = 14
open_backend [label = <
| Open Backend |
| MemoryStorage::new() / |
| SqliteStorage::open(path) / |
| FjallStorage::open(path) / ... |
>, fillcolor = "#F3E5F5", color = "#9C27B0"]
create_relation [label = "storage.create_relation(name, arity)", fillcolor = "#F3E5F5", color = "#9C27B0"]
}
subgraph cluster_write {
label = "Write (atomic batch via Transaction)"
style = "dashed"
color = "#4CAF50"
fontcolor = "#388E3C"
margin = 14
begin_tx [label = "storage.transaction()\n-> Box<dyn Transaction>", fillcolor = "#E8F5E9", color = "#4CAF50"]
tx_ops [label = <
| tx.insert / tx.delete |
| • insert yields pending RowId |
| • pending RowIds reused as FKs |
| • delete by RowId |
>, fillcolor = "#E8F5E9", color = "#4CAF50", shape = box]
commit [label = <
| tx.commit() |
| • native commit (LMDB, redb, SQLite, geomerge) |
| • buffered apply (memory, fjall) |
| • law validation (geomerge) |
| • yields CommittedTx |
>, fillcolor = "#E8F5E9", color = "#4CAF50", shape = box]
resolve_ids [label = <
| CommittedTx::resolve |
| • KV: pending == real |
| • geomerge: pending counter → (commit, counter) |
>, fillcolor = "#E8F5E9", color = "#4CAF50", shape = box]
}
subgraph cluster_read {
label = "Read"
style = "dashed"
color = "#FF9800"
fontcolor = "#F57C00"
margin = 14
scan_iter [label = "storage.scan_iter(name)\n-> RowStream", fillcolor = "#FFF3E0", color = "#FF9800"]
scan_where [label = "storage.scan_where(name, col, value)\n-> RowStream (filtered)", fillcolor = "#FFF3E0", color = "#FF9800"]
scan_full [label = "storage.scan(name)\n-> Vec<(RowId, Vec<Value>)>", fillcolor = "#FFF3E0", color = "#FF9800"]
}
subgraph cluster_output {
label = "Output"
style = "dashed"
color = "#888888"
fontcolor = "#555555"
margin = 18
rows_out [label = <
| Rows |
| • (RowId, Vec<Value>) |
| • consumed by query-ops |
| via scan_as_table |
>, fillcolor = "#ECEFF1", color = "#607D8B"]
}
// Setup
schema -> create_relation [color = "#2196F3"]
open_backend -> create_relation [color = "#9C27B0"]
// Write path
create_relation -> begin_tx [color = "#4CAF50"]
begin_tx -> tx_ops [color = "#4CAF50"]
row_data -> tx_ops [style = "dashed", color = "#2196F3"]
tx_ops -> commit [color = "#4CAF50"]
commit -> resolve_ids [label = "CommittedTx", color = "#4CAF50"]
// Read path
create_relation -> scan_iter [style = "dashed", color = "#9C27B0"]
create_relation -> scan_where [style = "dashed", color = "#9C27B0"]
create_relation -> scan_full [style = "dashed", color = "#9C27B0"]
commit -> scan_iter [style = "dashed", label = "after commit", color = "#4CAF50"]
// Output
scan_iter -> rows_out [color = "#FF9800"]
scan_where -> rows_out [color = "#FF9800"]
scan_full -> rows_out [color = "#FF9800"]
resolve_ids -> rows_out [style = "dashed", label = "real RowIds", color = "#4CAF50"]
}