1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
|
use std::path::PathBuf;
use serde::{Deserialize, Serialize};
use crate::{Error, Result, args::ServArgs};
const STYLE: &str = include_str!("../examples/simple-gruvbox.css");
const BOOKMARKS: &str = include_str!("../examples/bookmarks.json");
const FAVICON: &str = include_str!("../examples/favicon.svg");
#[derive(Deserialize, Serialize, Clone)]
pub struct Config {
pub port: u16,
pub style_file: PathBuf,
pub bookmarks_file: PathBuf,
pub favicon_file: PathBuf,
}
impl Config {
pub fn new(args: ServArgs) -> Result<Config> {
let config_home = Config::get_config_home()?;
let config_path = &config_home.join("config.toml");
let mut config = if config_path.exists() {
Config::load_config(config_path)?
} else {
Config::generate_defaults(config_home)?
};
config.override_with_serv_args(args)?;
Ok(config)
}
pub fn load_config(config: &PathBuf) -> Result<Config> {
let config = std::fs::read_to_string(&config)?;
let config: Config = toml::from_str(&config)?;
Ok(config)
}
pub fn generate_defaults(config_home: PathBuf) -> Result<Config> {
std::fs::create_dir_all(&config_home)?;
let style_file = config_home.join("style.css");
let bookmarks_file = config_home.join("bookmarks.json");
let favicon_file = config_home.join("favicon.svg");
let config_file = config_home.join("config.toml");
std::fs::write(&style_file, &STYLE)?;
std::fs::write(&bookmarks_file, &BOOKMARKS)?;
std::fs::write(&favicon_file, &FAVICON)?;
let config = Config {
port: 8080,
style_file,
bookmarks_file,
favicon_file,
};
let config_file_content = toml::to_string(&config)?;
std::fs::write(config_file, config_file_content)?;
Ok(config)
}
pub fn override_with_serv_args(&mut self, args: ServArgs) -> Result<()> {
if let Some(port) = &args.port {
self.port = port.parse::<u16>()?;
}
if let Some(style_file) = &args.style_file {
if PathBuf::from(style_file).exists() {
self.style_file = PathBuf::from(style_file)
}
}
if let Some(bookmarks_file) = &args.bookmarks_file {
if PathBuf::from(bookmarks_file).exists() {
self.bookmarks_file = PathBuf::from(bookmarks_file)
}
}
if let Some(favicon_file) = &args.favicon_file {
if PathBuf::from(favicon_file).exists() {
self.favicon_file = PathBuf::from(favicon_file)
}
}
Ok(())
}
fn get_config_home() -> Result<PathBuf> {
let config_home = if let Ok(xdg_config_home) = std::env::var("XDG_CONFIG_HOME") {
PathBuf::from(xdg_config_home).join("sbm-rs")
} else if let Ok(home) = std::env::var("HOME") {
PathBuf::from(home).join(".config/sbm-rs")
} else {
return Err(Error::ConfigHomeNotFound);
};
Ok(config_home)
}
}
|