Skip to content

Commit 34b8507

Browse files
committed
docs(architecture): detail gateway persistence
1 parent 71e1f74 commit 34b8507

1 file changed

Lines changed: 42 additions & 4 deletions

File tree

architecture/gateway.md

Lines changed: 42 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -56,10 +56,48 @@ names, creation timestamps, and labels. Crate-level details live in
5656

5757
## Persistence
5858

59-
The gateway stores protobuf payloads with indexed object metadata. SQLite is the
60-
default local store; Postgres is supported for deployments that need an external
61-
database. Persisted state includes sandboxes, providers, SSH sessions, policy
62-
revisions, settings, inference configuration, and deployment records.
59+
The gateway persistence layer is a protobuf object store. Domain services store
60+
typed protobuf messages as opaque binary payloads, while the database keeps a
61+
small set of indexed metadata columns for lookup, listing, versioning, and
62+
workflow state. The implementation lives in the
63+
[gateway persistence module](../crates/openshell-server/src/persistence/mod.rs);
64+
backend-specific SQL lives in the SQLite and Postgres migration directories
65+
under `crates/openshell-server/migrations/`.
66+
67+
The storage schema is intentionally narrow:
68+
69+
| Column | Purpose |
70+
|---|---|
71+
| `id` | Stable gateway-generated object ID and primary key. |
72+
| `object_type` | Logical resource kind, such as `sandbox`, `provider`, `ssh_session`, `inference_route`, `sandbox_policy`, or `draft_policy_chunk`. |
73+
| `name` | Human-readable name, unique within an object type when present. |
74+
| `scope` | Optional owner or namespace for scoped/versioned records, such as a sandbox ID for policy revisions. |
75+
| `version` | Optional monotonically increasing version for scoped records. |
76+
| `status` | Optional workflow state for records such as policy revisions or draft policy chunks. |
77+
| `dedup_key` and `hit_count` | Optional policy-advisor fields for coalescing repeated observations. |
78+
| `payload` | Prost-encoded protobuf payload for the full domain object. |
79+
| `created_at_ms` and `updated_at_ms` | Gateway timestamps used for ordering and list output. |
80+
| `labels` | JSON object carrying Kubernetes-style object labels for filtering and organization. |
81+
82+
Common resources use generic helpers that derive `object_type`, `id`, `name`,
83+
and labels from protobuf metadata traits before encoding the full message into
84+
`payload`. Policy revisions and draft policy chunks use the same table but also
85+
populate `scope`, `version`, `status`, `dedup_key`, and `hit_count` so the
86+
gateway can efficiently fetch the latest policy, track load status, and manage
87+
advisor drafts without creating resource-specific tables.
88+
89+
SQLite is the default local store; Postgres is supported for deployments that
90+
need an external database or multi-replica coordination. Both backends expose
91+
the same `Store` API and the same logical schema. Backend differences stay
92+
inside the adapters: for example, SQLite stores labels as JSON text and payloads
93+
as `BLOB`, while Postgres stores labels as `JSONB` and payloads as `BYTEA`.
94+
Domain code should depend on the object-store contract, not SQL dialect details.
95+
This keeps the gateway data model portable across storage backends and leaves
96+
room for future stores that can provide the same object, label, version, and
97+
scope semantics.
98+
99+
Persisted state includes sandboxes, providers, SSH sessions, policy revisions,
100+
settings, inference configuration, and deployment records.
63101

64102
Policy and runtime settings are delivered together through the effective sandbox
65103
config path. A gateway-global policy can override sandbox-scoped policy. The

0 commit comments

Comments
 (0)