| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112 |
- use std::fs::create_dir_all;
- use std::io::{self, Read, Write};
- use std::os::unix::net::{UnixListener, UnixStream};
- use std::sync::{Arc, Mutex};
- use std::thread;
-
- use twfss::{Database, SynchronizedDirectory};
-
- mod cli;
-
- fn config_dir() -> String {
- format!(
- "{}/.config/twfss",
- dirs::home_dir().unwrap().to_str().unwrap().to_owned()
- )
- }
-
- fn data_dir() -> String {
- format!(
- "{}/.local/share/twfss-client",
- dirs::home_dir().unwrap().to_str().unwrap().to_owned()
- )
- }
-
- fn db_path() -> String {
- format!("{}/client.db", data_dir())
- }
-
- fn main() {
- // Create the data directories if necessary.
- create_dir_all(config_dir()).unwrap();
- create_dir_all(data_dir()).unwrap();
-
- // Check whether the client is already running, and exit if it is.
- // TODO
-
- // TODO: Register signal handler for graceful shutdown.
-
- // Initialize the existing synchronized directories.
- let mut directories = Vec::new();
- let db = Arc::new(Mutex::new(Database::create_or_open(&db_path()).unwrap()));
- for directory in db.lock().unwrap().synchronized_directories() {
- // TODO: Error handling. If the directory was removed, remove it from the
- // list of synchronized directories.
- directories.push(SynchronizedDirectory::open(db.clone(), &directory, false).unwrap());
- }
-
- // Listen for CLI commands.
- // TODO: Graceful shutdown on errors.
- let listener = UnixListener::bind(cli::socket_path()).unwrap();
- for stream in listener.incoming() {
- match stream {
- Ok(stream) => {
- thread::spawn(move || {
- let mut stream = stream;
- match handle_cli_client(&mut stream) {
- Ok(()) => {}
- Err(e) => {
- // Log error and try to send it to the stream.
- // TODO
- write!(stream, "Error: {:?}", e).ok();
- }
- };
- });
- }
- Err(err) => {
- eprintln!("Error while listening on the local unix socket: {:?}", err);
- break;
- }
- }
- }
- }
-
- fn handle_cli_client(stream: &mut UnixStream) -> Result<(), Error> {
- let mut request = String::new();
- stream.read_to_string(&mut request)?;
-
- let options: cli::Options = serde_json::from_str(&request)?;
- let _verbose = options.verbose;
- match options.command {
- _cmd @ cli::Command::ListDirectories { .. } => {
- // TODO
- }
- _cmd @ cli::Command::AddDirectory { .. } => {
- // TODO
- }
- _cmd @ cli::Command::RemoveDirectory { .. } => {
- // TODO
- }
- }
-
- // TODO
- Ok(())
- }
-
- #[derive(Debug)]
- enum Error {
- Json(serde_json::error::Error),
- Io(std::io::Error),
- }
-
- impl From<serde_json::error::Error> for Error {
- fn from(e: serde_json::error::Error) -> Error {
- Error::Json(e)
- }
- }
-
- impl From<io::Error> for Error {
- fn from(e: io::Error) -> Error {
- Error::Io(e)
- }
- }
|