feat: start of better repo manager

concurrent-repos
Jef Roosens 2024-05-23 16:33:52 +02:00
parent 421f6ae69b
commit cc2dc9b28f
Signed by: Jef Roosens
GPG Key ID: B75D4F293C7052DB
8 changed files with 85 additions and 22 deletions

View File

@ -64,11 +64,11 @@ impl ReadFilter {
pub fn extension(&self) -> Option<&str> {
match self {
ReadFilter::None => Some(""),
ReadFilter::Gzip => Some(".gz"),
ReadFilter::Bzip2 => Some(".bz2"),
ReadFilter::Lzma => Some(".lzma"),
ReadFilter::Xz => Some(".xz"),
ReadFilter::Zstd => Some(".zst"),
ReadFilter::Gzip => Some("gz"),
ReadFilter::Bzip2 => Some("bz2"),
ReadFilter::Lzma => Some("lzma"),
ReadFilter::Xz => Some("xz"),
ReadFilter::Zstd => Some("zst"),
_ => None,
}
}

View File

@ -22,6 +22,7 @@ pub struct Model {
pub pgp_sig: Option<String>,
pub pgp_sig_size: Option<i64>,
pub sha256_sum: String,
pub compression: String,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]

View File

@ -3,13 +3,15 @@
use sea_orm::entity::prelude::*;
use serde::{Deserialize, Serialize};
use crate::db::PackageRelatedEnum;
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq, Serialize, Deserialize)]
#[sea_orm(table_name = "package_related")]
pub struct Model {
#[sea_orm(primary_key, auto_increment = false)]
pub package_id: i32,
#[sea_orm(primary_key, auto_increment = false)]
pub r#type: crate::db::PackageRelatedEnum,
pub r#type: PackageRelatedEnum,
#[sea_orm(primary_key, auto_increment = false)]
pub name: String,
}

View File

@ -52,6 +52,7 @@ impl MigrationTrait for Migration {
.col(ColumnDef::new(Package::PgpSig).string_len(255))
.col(ColumnDef::new(Package::PgpSigSize).big_integer())
.col(ColumnDef::new(Package::Sha256Sum).char_len(64).not_null())
.col(ColumnDef::new(Package::Compression).char_len(16).not_null())
.foreign_key(
ForeignKey::create()
.name("fk-package-repo_id")
@ -221,6 +222,7 @@ pub enum Package {
PgpSig,
PgpSigSize,
Sha256Sum,
Compression,
}
#[derive(Iden)]

View File

@ -45,20 +45,15 @@ pub async fn by_id(conn: &DbConn, id: i32) -> Result<Option<package::Model>> {
pub async fn by_fields(
conn: &DbConn,
repo_id: i32,
name: &str,
version: Option<&str>,
arch: &str,
name: &str,
) -> Result<Option<package::Model>> {
let mut query = Package::find()
Package::find()
.filter(package::Column::RepoId.eq(repo_id))
.filter(package::Column::Name.eq(name))
.filter(package::Column::Arch.eq(arch));
if let Some(version) = version {
query = query.filter(package::Column::Version.eq(version));
}
query.one(conn).await
.filter(package::Column::Arch.eq(arch))
.one(conn)
.await
}
pub async fn delete_with_arch(conn: &DbConn, repo_id: i32, arch: &str) -> Result<DeleteResult> {
@ -88,6 +83,7 @@ pub async fn insert(conn: &DbConn, repo_id: i32, pkg: crate::repo::package::Pack
pgp_sig: Set(info.pgpsig),
pgp_sig_size: Set(info.pgpsigsize),
sha256_sum: Set(info.sha256sum),
compression: Set(pkg.compression.extension().unwrap().to_string())
};
let pkg_entry = model.insert(conn).await?;

View File

@ -0,0 +1,62 @@
use std::path::{Path, PathBuf};
use sea_orm::{DbConn, ModelTrait};
use crate::db;
use crate::error::Result;
pub struct MetaRepoMngr {
repo_dir: PathBuf,
pkg_dir: PathBuf,
}
impl MetaRepoMngr {
pub fn new<P1: AsRef<Path>, P2: AsRef<Path>>(repo_dir: P1, pkg_dir: P2) -> Self {
MetaRepoMngr {
repo_dir: repo_dir.as_ref().to_path_buf(),
pkg_dir: pkg_dir.as_ref().to_path_buf(),
}
}
/// Remove the repo with the given name, if it existed
pub async fn remove_repo(&self, conn: &DbConn, repo: &str) -> Result<bool> {
let res = db::query::repo::by_name(conn, repo).await?;
if let Some(repo_entry) = res {
// Remove repository from database
repo_entry.delete(conn).await?;
// Remove files from file system
tokio::fs::remove_dir_all(self.repo_dir.join(repo)).await?;
tokio::fs::remove_dir_all(self.pkg_dir.join(repo)).await?;
Ok(true)
} else {
Ok(false)
}
}
pub async fn remove_pkg(
&self,
conn: &DbConn,
repo: &str,
arch: &str,
name: &str,
) -> Result<bool> {
let repo = db::query::repo::by_name(conn, repo).await?;
if let Some(repo) = repo {
let pkg = db::query::package::by_fields(conn, repo.id, arch, name).await?;
if let Some(pkg) = pkg {
// Remove package from database
pkg.delete(conn).await?;
Ok(true)
} else {
Ok(false)
}
} else {
Ok(false)
}
}
}

View File

@ -1,4 +1,5 @@
mod manager;
mod manager_new;
pub mod package;
pub use manager::RepoGroupManager;
@ -117,7 +118,8 @@ async fn post_package_archive(
let path_clone = path.clone();
let repo_clone = repo.clone();
let res = tokio::task::spawn_blocking(move || {
clone
global
.repo_manager
.write()
.unwrap()
.add_pkg_from_path(&repo_clone, &path_clone)
@ -144,9 +146,8 @@ async fn post_package_archive(
let res = db::query::package::by_fields(
&global.db,
repo_id,
&pkg.info.name,
None,
&pkg.info.arch,
&pkg.info.name,
)
.await?;
@ -242,9 +243,8 @@ async fn delete_package(
let res = db::query::package::by_fields(
&global.db,
repo_entry.id,
&name,
Some(&format!("{}-{}", version, release)),
&arch,
&name,
)
.await?;

View File

@ -193,7 +193,7 @@ impl Package {
// This unwrap should be safe, because we only allow passing through compressions with
// known file extensions
format!(
"{}.pkg.tar{}",
"{}.pkg.tar.{}",
self.full_name(),
self.compression.extension().unwrap()
)