Skip to main content

dreamwell_engine/
ids.rs

1//! Typed ID newtypes for stable cross-crate identification.
2
3use serde::{Deserialize, Serialize};
4
5/// Actor identity in the simulation.
6#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
7pub struct ActorId(pub u64);
8
9/// Entity identity (scene objects, topology nodes).
10#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
11pub struct EntityId(pub u64);
12
13/// Event identity in the canon pipeline.
14#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
15pub struct EventId(pub u64);
16
17/// World/universe identity.
18#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
19pub struct WorldId(pub u64);
20
21/// Scope key for canon event partitioning.
22#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
23pub struct ScopeKey(pub u64);
24
25/// Tick counter for deterministic time.
26#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
27pub struct Tick(pub u64);
28
29#[cfg(test)]
30mod tests {
31    use super::*;
32
33    #[test]
34    fn actor_id_equality() {
35        assert_eq!(ActorId(42), ActorId(42));
36        assert_ne!(ActorId(1), ActorId(2));
37    }
38
39    #[test]
40    fn entity_id_hash_stable() {
41        use std::collections::HashSet;
42        let mut set = HashSet::new();
43        set.insert(EntityId(100));
44        assert!(set.contains(&EntityId(100)));
45        assert!(!set.contains(&EntityId(101)));
46    }
47
48    #[test]
49    fn tick_ordering() {
50        assert!(Tick(1) < Tick(2));
51        assert!(Tick(0) <= Tick(0));
52    }
53
54    #[test]
55    fn serde_roundtrip() {
56        let id = ActorId(999);
57        let json = serde_json::to_string(&id).unwrap();
58        let back: ActorId = serde_json::from_str(&json).unwrap();
59        assert_eq!(id, back);
60    }
61}