Skip to main content

offline_intelligence/memory_db/
schema.rs

1// "D:\_ProjectWorks\AUDIO_Interface\Server\src\memory_db\schema.rs"
2//! Database schema definitions for the memory system
3
4use serde::{Deserialize, Serialize};
5use chrono::{DateTime, Utc};
6use std::collections::HashMap;
7
8/// Represents a conversation session
9#[derive(Debug, Clone, Serialize, Deserialize)]
10pub struct Session {
11    pub id: String,
12    pub created_at: DateTime<Utc>,
13    pub last_accessed: DateTime<Utc>,
14    pub metadata: SessionMetadata,
15}
16
17// Chat persistence: Session metadata with serde defaults for backward compatibility with existing database records
18#[derive(Debug, Clone, Serialize, Deserialize, Default)]
19pub struct SessionMetadata {
20    pub title: Option<String>,
21    #[serde(default)]  // Handle old records missing this field
22    pub tags: Vec<String>,
23    #[serde(default)]  // Handle old records missing this field
24    pub user_defined: HashMap<String, String>,
25    #[serde(default)]  // Handle old records missing this field
26    pub pinned: bool,
27}
28
29/// Represents a single message in a conversation
30#[derive(Debug, Clone, Serialize, Deserialize)]
31pub struct StoredMessage {
32    pub id: i64,
33    pub session_id: String,
34    pub message_index: i32,
35    pub role: String,
36    pub content: String,
37    pub tokens: i32,
38    pub timestamp: DateTime<Utc>,
39    pub importance_score: f32,
40    pub embedding_generated: bool,
41}
42
43/// Represents a conversation summary
44#[derive(Debug, Clone, Serialize, Deserialize)]
45pub struct Summary {
46    pub id: i64,
47    pub session_id: String,
48    pub message_range_start: i32,
49    pub message_range_end: i32,
50    pub summary_text: String,
51    pub compression_ratio: f32,
52    pub key_topics: Vec<String>,
53    pub generated_at: DateTime<Utc>,
54}
55
56/// Represents a preserved detail from a message
57#[derive(Debug, Clone, Serialize, Deserialize)]
58pub struct Detail {
59    pub id: i64,
60    pub session_id: String,
61    pub message_id: i64,
62    pub detail_type: String,
63    pub content: String,
64    pub context: String,
65    pub importance_score: f32,
66    pub accessed_count: i32,
67    pub last_accessed: DateTime<Utc>,
68}
69
70/// Represents an embedding vector for semantic search
71#[derive(Debug, Clone)]
72pub struct Embedding {
73    pub id: i64,
74    pub message_id: i64,
75    pub embedding: Vec<f32>,
76    pub embedding_model: String,
77    pub generated_at: DateTime<Utc>,
78}
79
80/// Cumulative summary of a session's full conversation history.
81/// There is exactly one row per session. It is replaced (not appended) on every
82/// KV cache clear, so it always covers everything from the start of the session.
83#[derive(Debug, Clone, Serialize, Deserialize)]
84pub struct SessionSummary {
85    pub session_id: String,
86    pub summary_text: String,
87    pub token_count: i32,
88    pub total_message_count: i32,
89    pub clear_count: i32,
90    pub last_updated: DateTime<Utc>,
91}
92
93/// Represents KV snapshot for cache management
94#[derive(Debug, Clone, Serialize, Deserialize)]
95pub struct KvSnapshot {
96    pub id: i64,
97    pub session_id: String,
98    pub message_id: i64,
99    pub snapshot_type: String,
100    pub kv_state: Vec<u8>,
101    pub kv_state_hash: String,
102    pub access_pattern: Option<String>,
103    pub size_bytes: i64,
104    pub created_at: DateTime<Utc>,
105}
106
107/// Represents search result
108#[derive(Debug, Clone)]
109pub struct SearchResult {
110    pub message: StoredMessage,
111    pub similarity_score: f32,
112    pub source: SearchSource,
113}
114
115#[derive(Debug, Clone)]
116pub enum SearchSource {
117    Semantic,
118    Keyword,
119    Hybrid,
120}
121
122/// Database statistics
123#[derive(Debug, Clone)]
124pub struct DatabaseStats {
125    pub total_sessions: i64,
126    pub total_messages: i64,
127    pub total_summaries: i64,
128    pub total_details: i64,
129    pub total_embeddings: i64,
130    pub database_size_bytes: i64,
131}
132
133/// SQL statements for table creation
134pub const SCHEMA_SQL: &str = "
135-- Sessions table
136CREATE TABLE IF NOT EXISTS sessions (
137    id TEXT PRIMARY KEY,
138    created_at TIMESTAMP NOT NULL,
139    last_accessed TIMESTAMP NOT NULL,
140    metadata TEXT NOT NULL
141);
142
143-- Messages table
144CREATE TABLE IF NOT EXISTS messages (
145    id INTEGER PRIMARY KEY AUTOINCREMENT,
146    session_id TEXT NOT NULL,
147    message_index INTEGER NOT NULL,
148    role TEXT NOT NULL,
149    content TEXT NOT NULL,
150    tokens INTEGER NOT NULL,
151    timestamp TIMESTAMP NOT NULL,
152    importance_score REAL NOT NULL DEFAULT 0.5,
153    embedding_generated BOOLEAN NOT NULL DEFAULT FALSE,
154    FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE,
155    UNIQUE(session_id, message_index)
156);
157
158-- Summaries table
159CREATE TABLE IF NOT EXISTS summaries (
160    id INTEGER PRIMARY KEY AUTOINCREMENT,
161    session_id TEXT NOT NULL,
162    message_range_start INTEGER NOT NULL,
163    message_range_end INTEGER NOT NULL,
164    summary_text TEXT NOT NULL,
165    compression_ratio REAL NOT NULL,
166    key_topics TEXT NOT NULL,
167    generated_at TIMESTAMP NOT NULL,
168    FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE,
169    UNIQUE(session_id, message_range_start, message_range_end)
170);
171
172-- Details table
173CREATE TABLE IF NOT EXISTS details (
174    id INTEGER PRIMARY KEY AUTOINCREMENT,
175    session_id TEXT NOT NULL,
176    message_id INTEGER NOT NULL,
177    detail_type TEXT NOT NULL,
178    content TEXT NOT NULL,
179    context TEXT NOT NULL,
180    importance_score REAL NOT NULL,
181    accessed_count INTEGER NOT NULL DEFAULT 0,
182    last_accessed TIMESTAMP NOT NULL,
183    FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE,
184    FOREIGN KEY (message_id) REFERENCES messages(id) ON DELETE CASCADE
185);
186
187-- Embeddings table
188CREATE TABLE IF NOT EXISTS embeddings (
189    id INTEGER PRIMARY KEY AUTOINCREMENT,
190    message_id INTEGER NOT NULL,
191    embedding BLOB NOT NULL,
192    embedding_model TEXT NOT NULL,
193    generated_at TIMESTAMP NOT NULL,
194    FOREIGN KEY (message_id) REFERENCES messages(id) ON DELETE CASCADE,
195    UNIQUE(message_id, embedding_model)
196);
197
198-- Indexes for performance
199CREATE INDEX IF NOT EXISTS idx_messages_session ON messages (session_id);
200CREATE INDEX IF NOT EXISTS idx_messages_timestamp ON messages (timestamp);
201CREATE INDEX IF NOT EXISTS idx_summaries_session ON summaries (session_id);
202CREATE INDEX IF NOT EXISTS idx_details_session ON details (session_id);
203CREATE INDEX IF NOT EXISTS idx_details_type ON details (detail_type);
204CREATE INDEX IF NOT EXISTS idx_embeddings_message ON embeddings (message_id);
205";