diff --git a/server/src/cli.rs b/server/src/cli.rs index 144e56e..0725e64 100644 --- a/server/src/cli.rs +++ b/server/src/cli.rs @@ -4,14 +4,25 @@ use crate::{Config, Global}; use axum::extract::FromRef; use axum::Router; use clap::Parser; +use std::io; use std::path::PathBuf; use std::sync::{Arc, RwLock}; use tower_http::trace::TraceLayer; +use tracing::debug; use tracing_subscriber::{layer::SubscriberExt, util::SubscriberInitExt}; #[derive(Parser)] #[command(author, version, about, long_about = None)] pub struct Cli { + /// Directory where package archives will be stored + pub pkg_dir: PathBuf, + /// Directory where repository metadata & SQLite database is stored + pub data_dir: PathBuf, + + /// Database connection URL; either sqlite:// or postgres://. Defaults to rieter.sqlite in the + /// data directory + #[arg(short, long)] + pub database_url: Option, /// Port the server will listen on #[arg(short, long, value_name = "PORT", default_value_t = 8000)] pub port: u16, @@ -22,10 +33,6 @@ pub struct Cli { default_value = "tower_http=debug,rieterd=debug" )] pub log: String, - /// Directory where package archives will be stored - pub pkg_dir: PathBuf, - /// Directory where repository metadata is stored - pub repo_dir: PathBuf, } impl FromRef for Arc> { @@ -42,19 +49,31 @@ impl Cli { .init(); } - pub async fn run(&self) { + pub async fn run(&self) -> crate::Result<()> { self.init_tracing(); - let db = crate::db::init("sqlite://test.db").await.unwrap(); + let db_url = if let Some(url) = &self.database_url { + url.clone() + } else { + format!( + "sqlite://{}", + self.data_dir.join("rieter.sqlite").to_string_lossy() + ) + }; + + debug!("Connecting to database with URL {}", db_url); + + let db = crate::db::init(db_url).await?; // let db = crate::db::init("postgres://rieter:rieter@localhost:5432/rieter") - // .await - // .unwrap(); + // .await + // .unwrap(); let config = Config { - repo_dir: self.repo_dir.clone(), + data_dir: self.data_dir.clone(), + repo_dir: self.data_dir.join("repos"), pkg_dir: self.pkg_dir.clone(), }; - let repo_manager = RepoGroupManager::new(&self.repo_dir, &self.pkg_dir); + let repo_manager = RepoGroupManager::new(&config.repo_dir, &self.pkg_dir); let global = Global { config, @@ -70,9 +89,11 @@ impl Cli { .layer(TraceLayer::new_for_http()); // run it with hyper on localhost:3000 - axum::Server::bind(&format!("0.0.0.0:{}", self.port).parse().unwrap()) - .serve(app.into_make_service()) - .await - .unwrap(); + Ok( + axum::Server::bind(&format!("0.0.0.0:{}", self.port).parse().unwrap()) + .serve(app.into_make_service()) + .await + .map_err(|err| io::Error::new(io::ErrorKind::Other, err))?, + ) } } diff --git a/server/src/main.rs b/server/src/main.rs index 8217909..e3dbf36 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -13,6 +13,7 @@ use std::sync::{Arc, RwLock}; #[derive(Clone)] pub struct Config { + data_dir: PathBuf, repo_dir: PathBuf, pkg_dir: PathBuf, } @@ -25,7 +26,7 @@ pub struct Global { } #[tokio::main] -async fn main() { +async fn main() -> crate::Result<()> { let cli = cli::Cli::parse(); - cli.run().await; + cli.run().await } diff --git a/server/src/repo/mod.rs b/server/src/repo/mod.rs index de3e74d..b2942a4 100644 --- a/server/src/repo/mod.rs +++ b/server/src/repo/mod.rs @@ -45,16 +45,17 @@ async fn post_package_archive( let clone = Arc::clone(&global.repo_manager); let path_clone = path.clone(); + let repo_clone = repo.clone(); let res = tokio::task::spawn_blocking(move || { - clone.write().unwrap().add_pkg_from_path(&repo, &path_clone) + clone.write().unwrap().add_pkg_from_path(&repo_clone, &path_clone) }) .await?; // Remove the downloaded file if the adding failed - if res.is_err() { + if let Err(err) = res { let _ = tokio::fs::remove_file(path).await; - return res; + return Err(err.into()); } let pkg = res.unwrap();