diff --git a/server/src/repo/manager.rs b/server/src/repo/manager.rs index d300f4c..df6ee17 100644 --- a/server/src/repo/manager.rs +++ b/server/src/repo/manager.rs @@ -131,7 +131,7 @@ impl RepoGroupManager { .join(format!("{}-{}", pkg.info.name, pkg.info.version)); // We first remove the previous version of the package, if present - self.remove_pkg_from_arch_repo(repo, arch, &pkg.info.name)?; + self.remove_pkg_from_arch_repo(repo, arch, &pkg.info.name, false)?; fs::create_dir_all(&pkg_dir)?; @@ -176,6 +176,7 @@ impl RepoGroupManager { repo: &str, arch: &str, pkg_name: &str, + sync: bool, ) -> io::Result { let arch_repo_dir = self.repo_dir.join(repo).join(arch); @@ -222,6 +223,10 @@ impl RepoGroupManager { }) })?; + if sync { + self.sync(repo, arch)?; + } + return Ok(true); } } diff --git a/server/src/repo/mod.rs b/server/src/repo/mod.rs index 4f5c573..17ad25a 100644 --- a/server/src/repo/mod.rs +++ b/server/src/repo/mod.rs @@ -26,6 +26,7 @@ pub fn router(global: &crate::Global) -> Router { .get(serve_repos.clone()), ) .route("/:repo/:arch", delete(delete_arch_repo)) + .route("/:repo/:arch/:filename", delete(delete_package)) .fallback(serve_repos) .with_state(global.clone()) } @@ -83,3 +84,34 @@ async fn delete_arch_repo( Ok(StatusCode::NOT_FOUND) } } + +async fn delete_package( + State(global): State, + Path((repo, arch, file_name)): Path<(String, String, String)>, +) -> crate::Result { + let name_parts = file_name.split('-').collect::>(); + + // Package archive files use the naming scheme pkgname-pkgver-pkgrel-arch, so a valid + // name contains at least 4 dash-separated sections + if name_parts.len() < 4 { + return Ok(StatusCode::NOT_FOUND); + } + + let name = name_parts[..name_parts.len() - 3].join("-"); + + let clone = Arc::clone(&global.repo_manager); + + let pkg_removed = tokio::task::spawn_blocking(move || { + clone + .write() + .unwrap() + .remove_pkg_from_arch_repo(&repo, &arch, &name, true) + }) + .await??; + + if pkg_removed { + Ok(StatusCode::OK) + } else { + Ok(StatusCode::NOT_FOUND) + } +}