Skip to main content

backbone_support/domain/entity/
mod.rs

1//! Domain Entities
2//!
3//! Generated by metaphor-schema. Do not edit manually.
4
5pub mod issue;
6pub mod service_level_agreement;
7pub mod service_level_priority;
8pub mod warranty_claim;
9pub mod issue_status;
10pub mod agreement_status;
11pub mod service_level_agreement_status;
12pub mod issue_priority;
13pub mod warranty_status;
14
15// Re-exports
16pub use issue::Issue;
17pub use issue::IssueBuilder;
18pub use issue::IssueId;
19pub use service_level_agreement::ServiceLevelAgreement;
20pub use service_level_agreement::ServiceLevelAgreementBuilder;
21pub use service_level_agreement::ServiceLevelAgreementId;
22pub use service_level_priority::ServiceLevelPriority;
23pub use service_level_priority::ServiceLevelPriorityBuilder;
24pub use service_level_priority::ServiceLevelPriorityId;
25pub use warranty_claim::WarrantyClaim;
26pub use warranty_claim::WarrantyClaimBuilder;
27pub use warranty_claim::WarrantyClaimId;
28pub use issue_status::IssueStatus;
29pub use agreement_status::AgreementStatus;
30pub use service_level_agreement_status::ServiceLevelAgreementStatus;
31pub use issue_priority::IssuePriority;
32pub use warranty_status::WarrantyStatus;
33
34// ==========================================================================
35// Entity Trait
36// ==========================================================================
37
38use std::fmt::Debug;
39
40/// Trait for domain entities
41///
42/// All generated entities implement this trait, providing
43/// a common interface for working with domain objects.
44pub trait Entity: Debug + Clone {
45    /// The type of the entity's unique identifier
46    type Id: Debug + Clone + PartialEq;
47
48    /// Get the entity's unique identifier
49    fn entity_id(&self) -> &Self::Id;
50
51    /// Get the entity type name
52    fn entity_type() -> &'static str;
53}
54
55// ==========================================================================
56// Audit Metadata
57// ==========================================================================
58
59use chrono::{DateTime, Utc};
60use serde::{Deserialize, Serialize};
61use uuid::Uuid;
62#[cfg(feature = "openapi")]
63use utoipa::ToSchema;
64
65/// Audit metadata stored as JSONB in the database
66///
67/// This struct consolidates audit fields (timestamps and actors) into a single
68/// JSONB column for efficient storage and flexible querying.
69#[derive(Debug, Clone, Default, Serialize, Deserialize, PartialEq)]
70#[cfg_attr(feature = "openapi", derive(ToSchema))]
71pub struct AuditMetadata {
72    /// Timestamp when the record was created
73    #[serde(skip_serializing_if = "Option::is_none")]
74    pub created_at: Option<DateTime<Utc>>,
75
76    /// Timestamp when the record was last updated
77    #[serde(skip_serializing_if = "Option::is_none")]
78    pub updated_at: Option<DateTime<Utc>>,
79
80    /// Timestamp when the record was soft-deleted
81    #[serde(skip_serializing_if = "Option::is_none")]
82    pub deleted_at: Option<DateTime<Utc>>,
83
84    /// User ID who created the record
85    #[serde(skip_serializing_if = "Option::is_none")]
86    pub created_by: Option<Uuid>,
87
88    /// User ID who last updated the record
89    #[serde(skip_serializing_if = "Option::is_none")]
90    pub updated_by: Option<Uuid>,
91
92    /// User ID who deleted the record
93    #[serde(skip_serializing_if = "Option::is_none")]
94    pub deleted_by: Option<Uuid>,
95}
96
97impl AuditMetadata {
98    /// Create new audit metadata with created_at set to now
99    pub fn new() -> Self {
100        Self {
101            created_at: Some(Utc::now()),
102            ..Default::default()
103        }
104    }
105
106    /// Create with creator ID
107    pub fn with_creator(creator_id: Uuid) -> Self {
108        Self {
109            created_at: Some(Utc::now()),
110            created_by: Some(creator_id),
111            ..Default::default()
112        }
113    }
114
115    /// Touch the record (update updated_at)
116    pub fn touch(&mut self) {
117        self.updated_at = Some(Utc::now());
118    }
119
120    /// Touch with updater ID
121    pub fn touch_by(&mut self, updater_id: Uuid) {
122        self.updated_at = Some(Utc::now());
123        self.updated_by = Some(updater_id);
124    }
125
126    /// Soft delete the record
127    pub fn soft_delete(&mut self) {
128        self.deleted_at = Some(Utc::now());
129    }
130
131    /// Soft delete with deleter ID
132    pub fn soft_delete_by(&mut self, deleter_id: Uuid) {
133        self.deleted_at = Some(Utc::now());
134        self.deleted_by = Some(deleter_id);
135    }
136
137    /// Restore a soft-deleted record
138    pub fn restore(&mut self) {
139        self.deleted_at = None;
140        self.deleted_by = None;
141    }
142
143    /// Check if record is deleted
144    pub fn is_deleted(&self) -> bool {
145        self.deleted_at.is_some()
146    }
147
148    /// Check if record is active (not deleted)
149    pub fn is_active(&self) -> bool {
150        self.deleted_at.is_none()
151    }
152}