1use serde::{Deserialize, Serialize};
4
5use crate::identity::IdentityId;
6use crate::receipt::ReceiptId;
7
8#[derive(Debug, Clone, PartialEq, Eq, Hash, Serialize, Deserialize)]
14pub struct ExperienceId(pub String);
15
16impl std::fmt::Display for ExperienceId {
17 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
18 write!(f, "{}", self.0)
19 }
20}
21
22#[derive(Debug, Clone, Serialize, Deserialize)]
24pub struct ExperienceEvent {
25 pub id: ExperienceId,
26 pub identity: IdentityId,
27 pub event_type: ExperienceType,
28 pub timestamp: u64,
29 pub duration: Option<u64>,
30 pub content_hash: String,
31 pub intensity: f32,
33
34 pub previous_experience_id: Option<ExperienceId>,
36 pub previous_experience_hash: Option<String>,
37 pub sequence_number: u64,
38 pub cumulative_hash: String,
39
40 pub signature: String,
41}
42
43#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
49pub enum ExperienceType {
50 Perception {
51 source: PerceptionSource,
52 },
53 Cognition {
54 cognition_type: CognitionType,
55 },
56 Action {
57 receipt_id: ReceiptId,
58 },
59 Communication {
60 direction: CommunicationDirection,
61 counterparty: IdentityId,
62 },
63 Memory {
64 operation: MemoryOpType,
65 },
66 Learning {
67 learning_type: LearningType,
68 domain: String,
69 },
70 Planning {
71 planning_type: PlanningType,
72 },
73 Emotion {
74 emotion_type: String,
75 },
76 Idle {
77 reason: String,
78 },
79 System {
80 event: SystemEvent,
81 },
82}
83
84impl ExperienceType {
85 pub fn as_tag(&self) -> &str {
87 match self {
88 Self::Perception { .. } => "perception",
89 Self::Cognition { .. } => "cognition",
90 Self::Action { .. } => "action",
91 Self::Communication { .. } => "communication",
92 Self::Memory { .. } => "memory",
93 Self::Learning { .. } => "learning",
94 Self::Planning { .. } => "planning",
95 Self::Emotion { .. } => "emotion",
96 Self::Idle { .. } => "idle",
97 Self::System { .. } => "system",
98 }
99 }
100}
101
102#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
103pub enum PerceptionSource {
104 Visual,
105 Auditory,
106 Text,
107 Sensor,
108}
109
110#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
111pub enum CognitionType {
112 Thought,
113 Reasoning,
114 Inference,
115 Recall,
116}
117
118#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
119pub enum CommunicationDirection {
120 Inbound,
121 Outbound,
122}
123
124#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
125pub enum MemoryOpType {
126 Store,
127 Retrieve,
128 Update,
129 Delete,
130}
131
132#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
133pub enum LearningType {
134 Supervised,
135 Unsupervised,
136 Reinforcement,
137 SelfDirected,
138}
139
140#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
141pub enum PlanningType {
142 GoalSetting,
143 PlanCreation,
144 PlanUpdate,
145}
146
147#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
148pub enum SystemEvent {
149 Startup,
150 Shutdown,
151 Checkpoint,
152 Error { message: String },
153}
154
155#[derive(Debug, Clone, Serialize, Deserialize)]
161pub struct ContinuityState {
162 pub identity: IdentityId,
163 pub genesis_experience_id: ExperienceId,
164 pub genesis_hash: String,
165 pub genesis_timestamp: u64,
166 pub latest_experience_id: ExperienceId,
167 pub latest_hash: String,
168 pub latest_timestamp: u64,
169 pub total_experiences: u64,
170}
171
172#[derive(Debug, Clone, PartialEq, Eq, Hash, Serialize, Deserialize)]
178pub struct AnchorId(pub String);
179
180impl std::fmt::Display for AnchorId {
181 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
182 write!(f, "{}", self.0)
183 }
184}
185
186#[derive(Debug, Clone, Serialize, Deserialize)]
188pub struct ContinuityAnchor {
189 pub id: AnchorId,
190 pub identity: IdentityId,
191 pub anchor_type: AnchorType,
192 pub experience_id: ExperienceId,
193 pub cumulative_hash: String,
194 pub experience_count: u64,
195 pub timestamp: u64,
196 pub previous_anchor: Option<AnchorId>,
197 pub external_witness: Option<String>,
198 pub signature: String,
199}
200
201#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
203pub enum AnchorType {
204 Genesis,
205 TimeBased { interval_hours: u32 },
206 ExperienceCount { interval: u64 },
207 Manual,
208 External { witness: IdentityId },
209}
210
211impl AnchorType {
212 pub fn as_tag(&self) -> &str {
214 match self {
215 Self::Genesis => "genesis",
216 Self::TimeBased { .. } => "time_based",
217 Self::ExperienceCount { .. } => "experience_count",
218 Self::Manual => "manual",
219 Self::External { .. } => "external",
220 }
221 }
222}
223
224#[derive(Debug, Clone, PartialEq, Eq, Hash, Serialize, Deserialize)]
230pub struct HeartbeatId(pub String);
231
232impl std::fmt::Display for HeartbeatId {
233 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
234 write!(f, "{}", self.0)
235 }
236}
237
238#[derive(Debug, Clone, Serialize, Deserialize)]
240pub struct HeartbeatRecord {
241 pub id: HeartbeatId,
242 pub identity: IdentityId,
243 pub timestamp: u64,
244 pub sequence_number: u64,
245 pub continuity_hash: String,
246 pub experience_count: u64,
247 pub experiences_since_last: u64,
248 pub status: HeartbeatStatus,
249 pub health: HealthMetrics,
250 pub signature: String,
251}
252
253#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
255pub enum HeartbeatStatus {
256 Active,
257 Idle,
258 Suspended,
259 Degraded,
260}
261
262impl HeartbeatStatus {
263 pub fn as_tag(&self) -> &str {
265 match self {
266 Self::Active => "active",
267 Self::Idle => "idle",
268 Self::Suspended => "suspended",
269 Self::Degraded => "degraded",
270 }
271 }
272}
273
274#[derive(Debug, Clone, Serialize, Deserialize)]
276pub struct HealthMetrics {
277 pub memory_usage_bytes: u64,
278 pub experience_rate_per_hour: f64,
279 pub error_count: u64,
280 pub latency_ms: u64,
281}
282
283#[derive(Debug, Clone, PartialEq, Eq, Hash, Serialize, Deserialize)]
289pub struct ClaimId(pub String);
290
291impl std::fmt::Display for ClaimId {
292 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
293 write!(f, "{}", self.0)
294 }
295}
296
297#[derive(Debug, Clone, Serialize, Deserialize)]
299pub struct ContinuityClaim {
300 pub id: ClaimId,
301 pub identity: IdentityId,
302 pub claim_type: ClaimType,
303 pub start_anchor: String,
304 pub start_timestamp: u64,
305 pub start_experience: u64,
306 pub end_anchor: String,
307 pub end_timestamp: u64,
308 pub end_experience: u64,
309 pub experience_count: u64,
310 pub max_gap_seconds: u64,
311 pub signature: String,
312}
313
314#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
316pub enum ClaimType {
317 FullContinuity,
318 RangeContinuity,
319 SinceContinuity,
320}
321
322impl ClaimType {
323 pub fn as_tag(&self) -> &str {
325 match self {
326 Self::FullContinuity => "full",
327 Self::RangeContinuity => "range",
328 Self::SinceContinuity => "since",
329 }
330 }
331}
332
333#[derive(Debug, Clone, Serialize, Deserialize)]
339pub struct Gap {
340 pub start: u64,
341 pub end: u64,
342 pub gap_type: GapType,
343 pub severity: GapSeverity,
344 pub impact: String,
345}
346
347#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
349pub enum GapType {
350 Temporal,
351 Sequence,
352 Hash,
353 Heartbeat,
354}
355
356#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
358pub enum GapSeverity {
359 Minor,
360 Moderate,
361 Major,
362 Critical,
363}
364
365#[derive(Debug, Clone)]
371pub struct ContinuityVerification {
372 pub claim_id: ClaimId,
373 pub chain_valid: bool,
374 pub anchors_valid: bool,
375 pub signatures_valid: bool,
376 pub gaps: Vec<Gap>,
377 pub result: ContinuityResult,
378 pub verified_at: u64,
379 pub errors: Vec<String>,
380}
381
382impl ContinuityVerification {
383 pub fn is_valid(&self) -> bool {
385 self.chain_valid && self.anchors_valid && self.signatures_valid && self.gaps.is_empty()
386 }
387}
388
389#[derive(Debug, Clone, PartialEq)]
391pub enum ContinuityResult {
392 Continuous,
393 Discontinuous {
394 gap_count: usize,
395 max_gap_seconds: u64,
396 },
397 Uncertain {
398 reason: String,
399 },
400}