Skip to main content

dactyl_db/
schema.rs

1//! Backend-neutral local schema inspection.
2//!
3//! This is the portable catalog surface. Callers do not need to depend on
4//! SQLite catalog queries or Neon metadata response shapes.
5
6use serde::{Deserialize, Serialize};
7
8/// Projection of the caller-visible schema for a physical store.
9#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
10pub struct StoreSchema {
11    /// Version of this backend-neutral schema description, not the file format.
12    pub format_version: u32,
13    pub tables: Vec<TableSchema>,
14    pub indexes: Vec<IndexSchema>,
15}
16
17impl StoreSchema {
18    pub fn table(&self, name: &str) -> Option<&TableSchema> {
19        let needle = name.to_ascii_lowercase();
20        self.tables
21            .iter()
22            .find(|table| table.name == needle || table.name == name)
23    }
24
25    pub fn row_count(&self) -> u64 {
26        self.tables.iter().map(|table| table.row_count).sum()
27    }
28}
29
30/// One table in the physical store.
31#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
32pub struct TableSchema {
33    pub name: String,
34    pub columns: Vec<ColumnSchema>,
35    pub unique_constraints: Vec<Vec<String>>,
36    pub foreign_keys: Vec<ForeignKeySchema>,
37    pub row_count: u64,
38}
39
40/// One column, including nullability and recorded default.
41#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
42pub struct ColumnSchema {
43    pub name: String,
44    pub primary_key: bool,
45    pub unique: bool,
46    pub not_null: bool,
47    pub default: Option<serde_json::Value>,
48}
49
50/// A structural index. This is not a query planner entry.
51#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
52pub struct IndexSchema {
53    pub name: String,
54    pub table: String,
55    pub columns: Vec<String>,
56    pub unique: bool,
57}
58
59/// A recorded foreign key and its delete action.
60#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
61pub struct ForeignKeySchema {
62    pub columns: Vec<String>,
63    pub ref_table: String,
64    pub ref_columns: Vec<String>,
65    pub on_delete: ForeignKeyAction,
66}
67
68/// Delete action reported by the physical store.
69#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
70#[serde(rename_all = "snake_case")]
71pub enum ForeignKeyAction {
72    NoAction,
73    Restrict,
74    Cascade,
75    SetNull,
76    SetDefault,
77}