Skip to main content

syncor_core/
link.rs

1use serde::{Deserialize, Serialize};
2use std::fmt;
3use std::path::PathBuf;
4
5/// A stable, deterministic identifier for a link derived from (repo, name).
6#[derive(Debug, Clone, PartialEq, Eq, Hash, Serialize, Deserialize)]
7pub struct LinkId(String);
8
9impl LinkId {
10    /// Create a deterministic ID from repo and name components.
11    pub fn from_parts(repo: &str, name: &str) -> Self {
12        use chkpt_core::store::blob::{bytes_to_hex, hash_content_bytes};
13        let input = format!("{}\0{}", repo, name);
14        let hash = hash_content_bytes(input.as_bytes());
15        Self(bytes_to_hex(&hash))
16    }
17
18    pub fn as_str(&self) -> &str {
19        &self.0
20    }
21}
22
23impl fmt::Display for LinkId {
24    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
25        f.write_str(&self.0)
26    }
27}
28
29/// How the link syncs changes between the local directory and the repo.
30#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
31#[serde(rename_all = "lowercase")]
32pub enum LinkMode {
33    /// Local changes are pushed to the repo.
34    Push,
35    /// Repo changes are pulled to the local directory.
36    Pull,
37}
38
39/// All persistent metadata about a single link.
40#[derive(Debug, Clone, Serialize, Deserialize)]
41pub struct LinkInfo {
42    pub id: LinkId,
43    pub name: String,
44    pub repo: String,
45    pub local_dir: PathBuf,
46    pub mode: LinkMode,
47    pub poll_interval_secs: Option<u64>,
48}
49
50/// Runtime state of a link (not persisted, tracked in-memory / SQLite).
51#[derive(Debug, Clone, Default, PartialEq, Eq)]
52pub enum LinkState {
53    #[default]
54    Idle,
55    Syncing,
56    Conflict,
57    Error(String),
58}