53 lines
1.5 KiB
Rust
53 lines
1.5 KiB
Rust
use std::{fs, path::PathBuf};
|
|
|
|
use anyhow::{Result, bail};
|
|
use directories::ProjectDirs;
|
|
use serde::{Deserialize, Serialize};
|
|
|
|
#[derive(Clone)]
|
|
pub struct Persistence {
|
|
config_dir: Option<PathBuf>,
|
|
}
|
|
|
|
impl Persistence {
|
|
pub fn new() -> Self {
|
|
Self {
|
|
config_dir: init_config_dir(),
|
|
}
|
|
}
|
|
|
|
pub fn save_config<T: Serialize>(&self, file: &str, data: &T) -> Result<()> {
|
|
if let Some(config_dir) = self.config_dir.as_ref() {
|
|
let bytes = serde_json::to_vec_pretty(data)?;
|
|
let filename = config_dir.join(file).with_extension("json");
|
|
fs::write(&filename, bytes)?;
|
|
}
|
|
Ok(())
|
|
}
|
|
|
|
pub fn load_config<T: for<'a> Deserialize<'a>>(&self, file: &str) -> Result<T> {
|
|
let Some(config_dir) = self.config_dir.as_ref() else {
|
|
bail!("config directory not found");
|
|
};
|
|
let filename = config_dir.join(file).with_extension("json");
|
|
let bytes = fs::read(filename)?;
|
|
Ok(serde_json::from_slice(&bytes)?)
|
|
}
|
|
}
|
|
|
|
fn init_config_dir() -> Option<PathBuf> {
|
|
let config_dir = project_dirs()?.config_dir().to_path_buf();
|
|
fs::create_dir_all(&config_dir).ok()?;
|
|
Some(config_dir)
|
|
}
|
|
|
|
pub fn init_data_dir() -> Option<PathBuf> {
|
|
let data_dir = project_dirs()?.data_dir().to_path_buf();
|
|
fs::create_dir_all(&data_dir).ok()?;
|
|
Some(data_dir)
|
|
}
|
|
|
|
fn project_dirs() -> Option<ProjectDirs> {
|
|
ProjectDirs::from("com", "virtual-boy", "Lemur")
|
|
}
|