feat: add initial models

This commit is contained in:
2026-02-28 12:23:06 +01:00
parent 66f7914ce0
commit 507cc7434e

64
src/model.rs Normal file
View File

@@ -0,0 +1,64 @@
use chrono::{DateTime, Utc};
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord)]
pub enum Priority {
Low,
Medium,
High,
Critical,
}
impl Default for Priority {
fn default() -> Self {
Self::Medium
}
}
impl std::fmt::Display for Priority {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::Low => write!(f, "low"),
Self::Medium => write!(f, "med"),
Self::High => write!(f, "high"),
Self::Critical => write!(f, "CRIT"),
}
}
}
impl std::str::FromStr for Priority {
type Err = anyhow::Error;
fn from_str(s: &str) -> Result<Self, Self::Err> {
match s.to_lowercase().as_str() {
"low" | "l" | "1" => Ok(Self::Low),
"medium" | "med" | "m" | "2" => Ok(Self::Medium),
"high" | "hi" | "h" | "3" => Ok(Self::High),
"critical" | "crit" | "c" | "4" => Ok(Self::Critical),
_ => anyhow::bail!("invalid priority: {s} (use low/medium/high/critical)"),
}
}
}
#[derive(Debug, Clone)]
pub struct Todo {
pub id: i64,
pub text: String,
pub priority: Priority,
pub project: Option<String>,
pub tags: Vec<String>,
pub created_at: DateTime<Utc>,
pub completed_at: Option<DateTime<Utc>>,
}
impl Todo {
pub fn is_done(&self) -> bool {
self.completed_at.is_some()
}
/// short project name (last path component)
pub fn project_short(&self) -> Option<&str> {
self.project
.as_deref()
.and_then(|p| p.rsplit('/').next())
}
}