db/models/
tickets.rs

1use chrono::{DateTime, Utc};
2use sea_orm::ActiveValue::Set;
3use sea_orm::DeriveActiveEnum;
4use sea_orm::entity::prelude::*;
5use serde::{Deserialize, Serialize};
6use strum::{Display, EnumString};
7
8#[derive(Clone, Debug, PartialEq, DeriveEntityModel)]
9#[sea_orm(table_name = "tickets")]
10pub struct Model {
11    #[sea_orm(primary_key)]
12    pub id: i64,
13
14    pub assignment_id: i64,
15    pub user_id: i64,
16
17    pub title: String,
18    pub description: String,
19
20    pub status: TicketStatus,
21
22    pub created_at: DateTime<Utc>,
23    pub updated_at: DateTime<Utc>,
24}
25
26#[derive(
27    Debug, Clone, PartialEq, EnumIter, DeriveActiveEnum, Display, EnumString, Serialize, Deserialize,
28)]
29#[serde(rename_all = "lowercase")]
30#[sea_orm(rs_type = "String", db_type = "Enum", enum_name = "ticket_status")]
31#[strum(serialize_all = "lowercase", ascii_case_insensitive)]
32pub enum TicketStatus {
33    #[sea_orm(string_value = "open")]
34    Open,
35
36    #[sea_orm(string_value = "closed")]
37    Closed,
38}
39
40#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
41pub enum Relation {
42    #[sea_orm(
43        belongs_to = "super::assignment::Entity",
44        from = "Column::AssignmentId",
45        to = "super::assignment::Column::Id"
46    )]
47    Assignment,
48
49    #[sea_orm(
50        belongs_to = "super::user::Entity",
51        from = "Column::UserId",
52        to = "super::user::Column::Id"
53    )]
54    User,
55}
56
57impl Related<super::assignment::Entity> for Entity {
58    fn to() -> RelationDef {
59        Relation::Assignment.def()
60    }
61}
62
63impl Related<super::user::Entity> for Entity {
64    fn to() -> RelationDef {
65        Relation::User.def()
66    }
67}
68
69impl ActiveModelBehavior for ActiveModel {}
70
71impl Model {
72    pub async fn create(
73        db: &DbConn,
74        assignment_id: i64,
75        user_id: i64,
76        title: &str,
77        description: &str,
78    ) -> Result<Model, DbErr> {
79        let now = Utc::now();
80
81        let active_model = ActiveModel {
82            assignment_id: Set(assignment_id),
83            user_id: Set(user_id),
84            title: Set(title.to_owned()),
85            description: Set(description.to_owned()),
86            status: Set(TicketStatus::Open),
87            created_at: Set(now),
88            updated_at: Set(now),
89            ..Default::default()
90        };
91
92        active_model.insert(db).await
93    }
94
95    pub async fn set_open(db: &DbConn, ticket_id: i64) -> Result<Model, DbErr> {
96        let model = Entity::find_by_id(ticket_id).one(db).await?;
97
98        let model = match model {
99            Some(m) => m,
100            None => return Err(DbErr::RecordNotFound("Ticket not found".to_string())),
101        };
102
103        let mut active_model: ActiveModel = model.into();
104
105        active_model.status = Set(TicketStatus::Open);
106        active_model.updated_at = Set(Utc::now());
107        active_model.update(db).await
108    }
109
110    pub async fn set_closed(db: &DbConn, ticket_id: i64) -> Result<Model, DbErr> {
111        let model = Entity::find_by_id(ticket_id).one(db).await?;
112
113        let model = match model {
114            Some(m) => m,
115            None => return Err(DbErr::RecordNotFound("Ticket not found".to_string())),
116        };
117
118        let mut active_model: ActiveModel = model.into();
119
120        active_model.status = Set(TicketStatus::Closed);
121        active_model.updated_at = Set(Utc::now());
122        active_model.update(db).await
123    }
124
125    pub async fn get_by_id(db: &DbConn, ticket_id: i64) -> Result<Option<Model>, DbErr> {
126        Entity::find_by_id(ticket_id).one(db).await
127    }
128
129    pub async fn delete(db: &DbConn, ticket_id: i64) -> Result<(), DbErr> {
130        Entity::delete_by_id(ticket_id).exec(db).await?;
131        Ok(())
132    }
133
134    pub async fn is_author(ticket_id: i64, user_id: i64, db: &DbConn) -> bool {
135        let ticket = Entity::find_by_id(ticket_id).one(db).await;
136        match ticket {
137            Ok(Some(t)) => t.user_id == user_id,
138            _ => false,
139        }
140    }
141}