git_bug/entities/issue/snapshot/
history_step.rs1use crate::{
15 entities::issue::{
16 Issue,
17 data::{label::Label, status::Status},
18 issue_operation::File,
19 },
20 replica::entity::{
21 id::entity_id::EntityId, identity::IdentityStub,
22 snapshot::timeline::history_step::HistoryStep, timestamp::TimeStamp,
23 },
24};
25
26#[derive(Debug)]
28pub struct NonEmptyVec<T> {
29 first: T,
30 rest: Vec<T>,
31}
32
33impl<T: Clone> Clone for NonEmptyVec<T> {
34 fn clone(&self) -> Self {
35 Self {
36 first: self.first.clone(),
37 rest: self.rest.clone(),
38 }
39 }
40}
41
42impl<T> NonEmptyVec<T> {
43 pub(super) fn new(item: T) -> Self {
44 Self {
45 first: item,
46 rest: vec![],
47 }
48 }
49
50 pub fn first(&self) -> &T {
53 &self.first
54 }
55
56 pub fn last(&self) -> &T {
59 self.rest.last().unwrap_or(&self.first)
60 }
61
62 pub(super) fn push(&mut self, item: T) {
63 self.rest.push(item);
64 }
65}
66
67#[derive(Debug, Clone)]
72pub enum IssueHistoryStep {
73 Comment(CommentItem),
75
76 Status(StatusHistoryStep),
78
79 Label(LabelHistoryStep),
81
82 Body(BodyHistoryStep),
84
85 Title(TitleHistoryStep),
87}
88
89impl HistoryStep for IssueHistoryStep {
90 fn author(&self) -> IdentityStub {
91 match self {
92 IssueHistoryStep::Comment(comment_item) => comment_item.history.first().author,
93 IssueHistoryStep::Status(status_history_step) => status_history_step.author,
94 IssueHistoryStep::Label(label_history_step) => label_history_step.author,
95 IssueHistoryStep::Body(body_history_step) => body_history_step.author,
96 IssueHistoryStep::Title(title_history_step) => title_history_step.author,
97 }
98 }
99
100 fn at(&self) -> TimeStamp {
101 match self {
102 IssueHistoryStep::Comment(comment_item) => comment_item.history.last().at,
103 IssueHistoryStep::Status(status_history_step) => status_history_step.at,
104 IssueHistoryStep::Label(label_history_step) => label_history_step.at,
105 IssueHistoryStep::Body(body_history_step) => body_history_step.at,
106 IssueHistoryStep::Title(title_history_step) => title_history_step.at,
107 }
108 }
109}
110
111#[derive(Debug, Clone)]
113pub struct CommentItem {
114 pub(crate) id: EntityId<Issue>,
115 pub(crate) history: NonEmptyVec<CommentHistoryStep>,
116}
117
118#[derive(Debug, Clone)]
120pub struct CommentHistoryStep {
121 pub author: IdentityStub,
123
124 pub message: String,
126
127 pub files: Vec<File>,
129
130 pub at: TimeStamp,
132}
133
134#[derive(Debug, Clone, Copy)]
136pub struct StatusHistoryStep {
137 pub author: IdentityStub,
139
140 pub status: Status,
142
143 pub at: TimeStamp,
145}
146
147#[derive(Debug, Clone)]
149pub struct LabelHistoryStep {
150 pub author: IdentityStub,
152
153 pub added: Vec<Label>,
155
156 pub removed: Vec<Label>,
158
159 pub at: TimeStamp,
161}
162
163#[derive(Debug, Clone)]
165pub struct BodyHistoryStep {
166 pub author: IdentityStub,
168
169 pub message: String,
171
172 pub files: Vec<File>,
174
175 pub at: TimeStamp,
177}
178
179#[derive(Debug, Clone)]
181pub struct TitleHistoryStep {
182 pub author: IdentityStub,
184
185 pub title: String,
187
188 pub at: TimeStamp,
190}