Skip to main content

vs_daemon/
config.rs

1//! Filesystem layout: where the daemon keeps state on disk.
2//!
3//! ```text
4//! ~/.vibesurfer/
5//!   daemon.sock           # the IPC socket
6//!   active-session        # one-line session id
7//!   state.db              # SQLite, WAL mode
8//!   key                   # AES-256 fallback if OS keyring unavailable
9//!   log/                  # rotating tracing output (M5+)
10//!   captures/             # screenshot output paths (M5+)
11//! ```
12
13use std::path::{Path, PathBuf};
14
15/// Daemon-side filesystem layout.
16#[derive(Debug, Clone)]
17pub struct Paths {
18    /// Root directory; usually `$HOME/.vibesurfer`.
19    pub root: PathBuf,
20}
21
22impl Paths {
23    /// Construct from a custom root (tests use a temp dir).
24    #[must_use]
25    pub fn at(root: impl Into<PathBuf>) -> Self {
26        Self { root: root.into() }
27    }
28
29    /// Conventional location: `$HOME/.vibesurfer`. Falls back to the
30    /// current directory if `$HOME` is unset (rare; CI containers).
31    #[must_use]
32    pub fn home() -> Self {
33        let root = std::env::var_os("HOME").map_or_else(
34            || PathBuf::from(".vibesurfer"),
35            |h| Path::new(&h).join(".vibesurfer"),
36        );
37        Self::at(root)
38    }
39
40    #[must_use]
41    pub fn socket(&self) -> PathBuf {
42        self.root.join("daemon.sock")
43    }
44
45    #[must_use]
46    pub fn db(&self) -> PathBuf {
47        self.root.join("state.db")
48    }
49
50    #[must_use]
51    pub fn active_session(&self) -> PathBuf {
52        self.root.join("active-session")
53    }
54
55    #[must_use]
56    pub fn key_file(&self) -> PathBuf {
57        self.root.join("key")
58    }
59
60    /// Where the daemon writes screenshot PNGs from `vs_capture`.
61    /// Defaults to `<root>/captures`. Overridable per-process via the
62    /// `VS_CAPTURES_DIR` environment variable.
63    #[must_use]
64    pub fn captures(&self) -> PathBuf {
65        if let Some(p) = std::env::var_os("VS_CAPTURES_DIR") {
66            return PathBuf::from(p);
67        }
68        self.root.join("captures")
69    }
70
71    /// Ensure the root directory exists.
72    pub fn ensure_root(&self) -> std::io::Result<()> {
73        std::fs::create_dir_all(&self.root)
74    }
75}