159 lines
3.7 KiB
Rust
159 lines
3.7 KiB
Rust
#![recursion_limit = "128"]
|
|
|
|
extern crate ape;
|
|
extern crate app_dirs;
|
|
extern crate core;
|
|
#[macro_use]
|
|
extern crate error_chain;
|
|
extern crate getopts;
|
|
extern crate hyper;
|
|
extern crate id3;
|
|
extern crate image;
|
|
extern crate iron;
|
|
extern crate lewton;
|
|
extern crate metaflac;
|
|
extern crate mount;
|
|
extern crate params;
|
|
extern crate reqwest;
|
|
extern crate regex;
|
|
extern crate secure_session;
|
|
extern crate serde;
|
|
#[macro_use]
|
|
extern crate serde_derive;
|
|
extern crate serde_json;
|
|
extern crate staticfile;
|
|
extern crate sqlite;
|
|
extern crate toml;
|
|
extern crate typemap;
|
|
extern crate url;
|
|
|
|
#[cfg(windows)]
|
|
extern crate uuid;
|
|
#[cfg(windows)]
|
|
extern crate winapi;
|
|
#[cfg(windows)]
|
|
extern crate kernel32;
|
|
#[cfg(windows)]
|
|
extern crate shell32;
|
|
#[cfg(windows)]
|
|
extern crate user32;
|
|
|
|
#[cfg(unix)]
|
|
extern crate unix_daemonize;
|
|
|
|
#[cfg(unix)]
|
|
use unix_daemonize::{daemonize_redirect, ChdirMode};
|
|
|
|
use errors::*;
|
|
use getopts::Options;
|
|
use iron::prelude::*;
|
|
use mount::Mount;
|
|
use staticfile::Static;
|
|
use std::path::Path;
|
|
use std::sync::Arc;
|
|
|
|
mod api;
|
|
mod collection;
|
|
mod config;
|
|
mod ddns;
|
|
mod errors;
|
|
mod index;
|
|
mod metadata;
|
|
mod ui;
|
|
mod utils;
|
|
mod thumbnails;
|
|
mod vfs;
|
|
|
|
fn main() {
|
|
if let Err(ref e) = run() {
|
|
println!("Error: {}", e);
|
|
|
|
for e in e.iter().skip(1) {
|
|
println!("caused by: {}", e);
|
|
}
|
|
if let Some(backtrace) = e.backtrace() {
|
|
println!("backtrace: {:?}", backtrace);
|
|
}
|
|
::std::process::exit(1);
|
|
}
|
|
}
|
|
|
|
#[cfg(unix)]
|
|
fn daemonize() -> Result<()> {
|
|
let mut log_file = utils::get_data_root()?;
|
|
log_file.push("polaris.log");
|
|
match daemonize_redirect(Some(&log_file), Some(&log_file), ChdirMode::NoChdir) {
|
|
Ok(_) => Ok(()),
|
|
Err(_) => bail!(ErrorKind::DaemonError),
|
|
}
|
|
}
|
|
|
|
fn run() -> Result<()> {
|
|
|
|
#[cfg(unix)]
|
|
daemonize()?;
|
|
|
|
// Parse CLI options
|
|
let args: Vec<String> = std::env::args().collect();
|
|
let mut options = Options::new();
|
|
options.optopt("c", "config", "set the configuration file", "FILE");
|
|
options.optopt("d", "database", "set the path to index database", "FILE");
|
|
options.optopt("w", "web", "set the path to web client files", "DIRECTORY");
|
|
let matches = options.parse(&args[1..])?;
|
|
|
|
// Parse config
|
|
let config_file_name = matches.opt_str("c");
|
|
let config_file_path = config_file_name.map(|n| Path::new(n.as_str()).to_path_buf());
|
|
let mut config = config::Config::parse(config_file_path)?;
|
|
|
|
// Init VFS
|
|
let vfs = Arc::new(vfs::Vfs::new(config.vfs.clone()));
|
|
|
|
// Init index
|
|
println!("Starting up index");
|
|
let index_file_name = matches.opt_str("d");
|
|
let index_file_path = index_file_name.map(|n| Path::new(n.as_str()).to_path_buf());
|
|
config.index.path = index_file_path.unwrap_or( config.index.path );
|
|
let index = Arc::new(index::Index::new(vfs.clone(), &config.index)?);
|
|
let index_ref = index.clone();
|
|
std::thread::spawn(move || index_ref.run());
|
|
|
|
// Mount API
|
|
println!("Mounting API");
|
|
let mut mount = Mount::new();
|
|
let mut collection = collection::Collection::new(vfs, index);
|
|
collection.load_config(&config)?;
|
|
let handler = api::get_handler(collection, &config.secret);
|
|
mount.mount("/api/", handler);
|
|
|
|
// Mount static files
|
|
println!("Mounting static files");
|
|
let web_dir_name = matches.opt_str("w");
|
|
let mut default_web_dir = utils::get_data_root()?;
|
|
default_web_dir.push("web");
|
|
let web_dir_path = web_dir_name
|
|
.map(|n| Path::new(n.as_str()).to_path_buf())
|
|
.unwrap_or(default_web_dir);
|
|
|
|
mount.mount("/", Static::new(web_dir_path));
|
|
|
|
println!("Starting up server");
|
|
let mut server = Iron::new(mount).http(("0.0.0.0", 5050))?;
|
|
|
|
// Start DDNS updates
|
|
match config.ddns {
|
|
Some(ref ddns_config) => {
|
|
let ddns_config = ddns_config.clone();
|
|
std::thread::spawn(|| { ddns::run(ddns_config); });
|
|
}
|
|
None => (),
|
|
};
|
|
|
|
// Run UI
|
|
ui::run();
|
|
|
|
println!("Shutting down server");
|
|
server.close()?;
|
|
|
|
Ok(())
|
|
}
|