From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from firstgate.proxmox.com (firstgate.proxmox.com [212.224.123.68]) by lore.proxmox.com (Postfix) with ESMTPS id 742C01FF2CF for ; Tue, 9 Jul 2024 08:18:49 +0200 (CEST) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id 6129E18768; Tue, 9 Jul 2024 08:19:11 +0200 (CEST) From: Wolfgang Bumiller To: pbs-devel@lists.proxmox.com Date: Tue, 9 Jul 2024 08:18:30 +0200 Message-Id: <20240709061832.52121-4-w.bumiller@proxmox.com> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20240709061832.52121-1-w.bumiller@proxmox.com> References: <20240709061832.52121-1-w.bumiller@proxmox.com> MIME-Version: 1.0 X-SPAM-LEVEL: Spam detection results: 0 AWL 0.086 Adjusted score from AWL reputation of From: address BAYES_00 -1.9 Bayes spam probability is 0 to 1% DMARC_MISSING 0.1 Missing DMARC policy KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_PASS -0.001 SPF: sender matches SPF record Subject: [pbs-devel] [PATCH proxmox 4/6] apt: use api types from apt-api-types crate X-BeenThere: pbs-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox Backup Server development discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: Proxmox Backup Server development discussion Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: pbs-devel-bounces@lists.proxmox.com Sender: "pbs-devel" From: Dietmar Maurer Signed-off-by: Dietmar Maurer --- proxmox-apt/Cargo.toml | 5 +- proxmox-apt/debian/control | 10 +- proxmox-apt/src/repositories/file.rs | 119 ++--------- .../src/repositories/file/list_parser.rs | 2 +- .../src/repositories/file/sources_parser.rs | 2 +- proxmox-apt/src/repositories/mod.rs | 37 ++-- proxmox-apt/src/repositories/repository.rs | 187 +----------------- proxmox-apt/src/repositories/standard.rs | 107 +--------- proxmox-apt/tests/repositories.rs | 24 +-- 9 files changed, 65 insertions(+), 428 deletions(-) diff --git a/proxmox-apt/Cargo.toml b/proxmox-apt/Cargo.toml index 34573543..bbd4ff89 100644 --- a/proxmox-apt/Cargo.toml +++ b/proxmox-apt/Cargo.toml @@ -8,7 +8,7 @@ license.workspace = true repository.workspace = true homepage.workspace = true -exclude = [ "debian" ] +exclude = ["debian"] [dependencies] anyhow.workspace = true @@ -20,4 +20,5 @@ serde_json.workspace = true rfc822-like = "0.2.1" -proxmox-schema = { workspace = true, features = [ "api-macro" ] } +proxmox-apt-api-types.workspace = true +proxmox-config-digest = { workspace = true, features = ["openssl"] } diff --git a/proxmox-apt/debian/control b/proxmox-apt/debian/control index c3248212..347631e6 100644 --- a/proxmox-apt/debian/control +++ b/proxmox-apt/debian/control @@ -10,8 +10,9 @@ Build-Depends: debhelper (>= 12), librust-hex-0.4+default-dev , librust-once-cell-1+default-dev (>= 1.3.1-~~) , librust-openssl-0.10+default-dev , - librust-proxmox-schema-3+api-macro-dev (>= 3.1.1-~~) , - librust-proxmox-schema-3+default-dev (>= 3.1.1-~~) , + librust-proxmox-apt-api-types-1+default-dev , + librust-proxmox-config-digest-0.1+default-dev , + librust-proxmox-config-digest-0.1+openssl-dev , librust-rfc822-like-0.2+default-dev (>= 0.2.1-~~) , librust-serde-1+default-dev , librust-serde-1+derive-dev , @@ -33,8 +34,9 @@ Depends: librust-hex-0.4+default-dev, librust-once-cell-1+default-dev (>= 1.3.1-~~), librust-openssl-0.10+default-dev, - librust-proxmox-schema-3+api-macro-dev (>= 3.1.1-~~), - librust-proxmox-schema-3+default-dev (>= 3.1.1-~~), + librust-proxmox-apt-api-types-1+default-dev, + librust-proxmox-config-digest-0.1+default-dev, + librust-proxmox-config-digest-0.1+openssl-dev, librust-rfc822-like-0.2+default-dev (>= 0.2.1-~~), librust-serde-1+default-dev, librust-serde-1+derive-dev, diff --git a/proxmox-apt/src/repositories/file.rs b/proxmox-apt/src/repositories/file.rs index 086abf49..21f612ef 100644 --- a/proxmox-apt/src/repositories/file.rs +++ b/proxmox-apt/src/repositories/file.rs @@ -1,123 +1,29 @@ -use std::fmt::Display; use std::path::{Path, PathBuf}; use anyhow::{format_err, Error}; -use serde::{Deserialize, Serialize}; use crate::repositories::release::DebianCodename; -use crate::repositories::repository::{ - APTRepository, APTRepositoryFileType, APTRepositoryPackageType, +use proxmox_apt_api_types::{ + APTRepository, APTRepositoryFile, APTRepositoryFileError, APTRepositoryFileType, + APTRepositoryInfo, APTRepositoryPackageType, }; use crate::repositories::repository::APTRepositoryImpl; -use proxmox_schema::api; - mod list_parser; use list_parser::APTListFileParser; mod sources_parser; use sources_parser::APTSourcesFileParser; +use proxmox_config_digest::ConfigDigest; + trait APTRepositoryParser { /// Parse all repositories including the disabled ones and push them onto /// the provided vector. fn parse_repositories(&mut self) -> Result, Error>; } -#[api( - properties: { - "file-type": { - type: APTRepositoryFileType, - }, - repositories: { - description: "List of APT repositories.", - type: Array, - items: { - type: APTRepository, - }, - }, - digest: { - description: "Digest for the content of the file.", - optional: true, - type: Array, - items: { - description: "Digest byte.", - type: u8, - }, - }, - }, -)] -#[derive(Debug, Clone, Serialize, Deserialize)] -#[serde(rename_all = "kebab-case")] -/// Represents an abstract APT repository file. -pub struct APTRepositoryFile { - /// The path to the file. If None, `contents` must be set directly. - #[serde(skip_serializing_if = "Option::is_none")] - pub path: Option, - - /// The type of the file. - pub file_type: APTRepositoryFileType, - - /// List of repositories in the file. - pub repositories: Vec, - - /// The file content, if already parsed. - #[serde(skip_serializing_if = "Option::is_none")] - pub content: Option, - - /// Digest of the original contents. - #[serde(skip_serializing_if = "Option::is_none")] - pub digest: Option<[u8; 32]>, -} - -#[api] -#[derive(Debug, Clone, Serialize, Deserialize)] -#[serde(rename_all = "kebab-case")] -/// Error type for problems with APT repository files. -pub struct APTRepositoryFileError { - /// The path to the problematic file. - pub path: String, - - /// The error message. - pub error: String, -} - -impl Display for APTRepositoryFileError { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - write!(f, "proxmox-apt error for '{}' - {}", self.path, self.error) - } -} - -impl std::error::Error for APTRepositoryFileError { - fn source(&self) -> Option<&(dyn std::error::Error + 'static)> { - None - } -} - -#[api] -#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Serialize, Deserialize)] -#[serde(rename_all = "kebab-case")] -/// Additional information for a repository. -pub struct APTRepositoryInfo { - /// Path to the defining file. - #[serde(default, skip_serializing_if = "String::is_empty")] - pub path: String, - - /// Index of the associated respository within the file (starting from 0). - pub index: usize, - - /// The property from which the info originates (e.g. "Suites") - #[serde(skip_serializing_if = "Option::is_none")] - pub property: Option, - - /// Info kind (e.g. "warning") - pub kind: String, - - /// Info message - pub message: String, -} - pub trait APTRepositoryFileImpl { /// Creates a new `APTRepositoryFile` without parsing. /// @@ -131,7 +37,7 @@ pub trait APTRepositoryFileImpl { /// Check if the file exists. fn exists(&self) -> bool; - fn read_with_digest(&self) -> Result<(Vec, [u8; 32]), APTRepositoryFileError>; + fn read_with_digest(&self) -> Result<(Vec, ConfigDigest), APTRepositoryFileError>; /// Create an `APTRepositoryFileError`. fn err(&self, error: Error) -> APTRepositoryFileError; @@ -213,7 +119,8 @@ impl APTRepositoryFileImpl for APTRepositoryFile { return Ok(None); } - let file_type = APTRepositoryFileType::try_from(&extension[..]) + let file_type = extension[..] + .parse() .map_err(|_| new_err("invalid extension"))?; if !file_name @@ -250,15 +157,15 @@ impl APTRepositoryFileImpl for APTRepositoryFile { } } - fn read_with_digest(&self) -> Result<(Vec, [u8; 32]), APTRepositoryFileError> { + fn read_with_digest(&self) -> Result<(Vec, ConfigDigest), APTRepositoryFileError> { if let Some(path) = &self.path { let content = std::fs::read(path).map_err(|err| self.err(format_err!("{}", err)))?; - let digest = openssl::sha::sha256(&content); + let digest = ConfigDigest::from_slice(&content); Ok((content, digest)) } else if let Some(ref content) = self.content { let content = content.as_bytes(); - let digest = openssl::sha::sha256(content); + let digest = ConfigDigest::from_slice(content); Ok((content.to_vec(), digest)) } else { Err(self.err(format_err!( @@ -308,13 +215,13 @@ impl APTRepositoryFileImpl for APTRepositoryFile { } }; - if let Some(digest) = self.digest { + if let Some(digest) = &self.digest { if !self.exists() { return Err(self.err(format_err!("digest specified, but file does not exist"))); } let (_, current_digest) = self.read_with_digest()?; - if digest != current_digest { + if digest != ¤t_digest { return Err(self.err(format_err!("digest mismatch"))); } } diff --git a/proxmox-apt/src/repositories/file/list_parser.rs b/proxmox-apt/src/repositories/file/list_parser.rs index 93bbcc12..8681509a 100644 --- a/proxmox-apt/src/repositories/file/list_parser.rs +++ b/proxmox-apt/src/repositories/file/list_parser.rs @@ -184,7 +184,7 @@ impl APTListFileParser { // e.g. quoted "deb" is not accepted by APT, so no need for quote word parsing here line = match line.split_once(|c| char::is_ascii_whitespace(&c)) { Some((package_type, rest)) => { - repo.types.push(package_type.try_into()?); + repo.types.push(package_type.parse()?); rest } None => return Ok(None), // empty line diff --git a/proxmox-apt/src/repositories/file/sources_parser.rs b/proxmox-apt/src/repositories/file/sources_parser.rs index 213db9d6..017162bb 100644 --- a/proxmox-apt/src/repositories/file/sources_parser.rs +++ b/proxmox-apt/src/repositories/file/sources_parser.rs @@ -108,7 +108,7 @@ impl APTSourcesFileParser { } let mut types = Vec::::new(); for package_type in values { - types.push((&package_type[..]).try_into()?); + types.push((&package_type[..]).parse()?); } repo.types = types; } diff --git a/proxmox-apt/src/repositories/mod.rs b/proxmox-apt/src/repositories/mod.rs index 014f1820..7768a47a 100644 --- a/proxmox-apt/src/repositories/mod.rs +++ b/proxmox-apt/src/repositories/mod.rs @@ -4,21 +4,22 @@ use std::path::PathBuf; use anyhow::{bail, Error}; mod repository; -pub use repository::APTRepositoryImpl; -pub use repository::{ - APTRepository, APTRepositoryFileType, APTRepositoryOption, APTRepositoryPackageType, +use proxmox_apt_api_types::{ + APTRepository, APTRepositoryFile, APTRepositoryFileError, APTRepositoryFileType, + APTRepositoryHandle, APTRepositoryInfo, APTRepositoryOption, APTRepositoryPackageType, + APTStandardRepository, }; +use proxmox_config_digest::ConfigDigest; +pub use repository::APTRepositoryImpl; mod file; pub use file::APTRepositoryFileImpl; -pub use file::{APTRepositoryFile, APTRepositoryFileError, APTRepositoryInfo}; mod release; pub use release::{get_current_release_codename, DebianCodename}; mod standard; -pub use standard::APTRepositoryHandleImpl; -pub use standard::{APTRepositoryHandle, APTStandardRepository}; +pub use standard::{APTRepositoryHandleImpl, APTStandardRepositoryImpl}; const APT_SOURCES_LIST_FILENAME: &str = "/etc/apt/sources.list"; const APT_SOURCES_LIST_DIRECTORY: &str = "/etc/apt/sources.list.d/"; @@ -28,7 +29,7 @@ const APT_SOURCES_LIST_DIRECTORY: &str = "/etc/apt/sources.list.d/"; /// The digest is invariant with respect to file order. /// /// Files without a digest are ignored. -fn common_digest(files: &[APTRepositoryFile]) -> [u8; 32] { +fn common_digest(files: &[APTRepositoryFile]) -> ConfigDigest { let mut digests = BTreeMap::new(); for file in files.iter() { @@ -43,7 +44,7 @@ fn common_digest(files: &[APTRepositoryFile]) -> [u8; 32] { } } - openssl::sha::sha256(&common_raw[..]) + ConfigDigest::from_slice(&common_raw[..]) } /// Provides additional information about the repositories. @@ -86,22 +87,22 @@ pub fn standard_repositories( suite: DebianCodename, ) -> Vec { let mut result = vec![ - APTStandardRepository::from(APTRepositoryHandle::Enterprise), - APTStandardRepository::from(APTRepositoryHandle::NoSubscription), - APTStandardRepository::from(APTRepositoryHandle::Test), + APTStandardRepository::from_handle(APTRepositoryHandle::Enterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::NoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::Test), ]; if product == "pve" { result.append(&mut vec![ - APTStandardRepository::from(APTRepositoryHandle::CephQuincyEnterprise), - APTStandardRepository::from(APTRepositoryHandle::CephQuincyNoSubscription), - APTStandardRepository::from(APTRepositoryHandle::CephQuincyTest), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyEnterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyNoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyTest), ]); if suite == DebianCodename::Bookworm { result.append(&mut vec![ - APTStandardRepository::from(APTRepositoryHandle::CephReefEnterprise), - APTStandardRepository::from(APTRepositoryHandle::CephReefNoSubscription), - APTStandardRepository::from(APTRepositoryHandle::CephReefTest), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefEnterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefNoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefTest), ]); } } @@ -128,7 +129,7 @@ pub fn standard_repositories( pub type Repositories = ( Vec, Vec, - [u8; 32], + ConfigDigest, ); /// Returns all APT repositories configured in `/etc/apt/sources.list` and diff --git a/proxmox-apt/src/repositories/repository.rs b/proxmox-apt/src/repositories/repository.rs index a07db7cb..596c6385 100644 --- a/proxmox-apt/src/repositories/repository.rs +++ b/proxmox-apt/src/repositories/repository.rs @@ -1,193 +1,12 @@ -use std::fmt::Display; use std::io::{BufRead, BufReader, Write}; use std::path::PathBuf; use anyhow::{bail, format_err, Error}; -use serde::{Deserialize, Serialize}; -use proxmox_schema::api; - -use crate::repositories::standard::APTRepositoryHandle; use crate::repositories::standard::APTRepositoryHandleImpl; - -#[api] -#[derive(Debug, Copy, Clone, Serialize, Deserialize, PartialEq, Eq)] -#[serde(rename_all = "lowercase")] -pub enum APTRepositoryFileType { - /// One-line-style format - List, - /// DEB822-style format - Sources, -} - -impl TryFrom<&str> for APTRepositoryFileType { - type Error = Error; - - fn try_from(file_type: &str) -> Result { - match file_type { - "list" => Ok(APTRepositoryFileType::List), - "sources" => Ok(APTRepositoryFileType::Sources), - _ => bail!("invalid file type '{file_type}'"), - } - } -} - -impl Display for APTRepositoryFileType { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match self { - APTRepositoryFileType::List => write!(f, "list"), - APTRepositoryFileType::Sources => write!(f, "sources"), - } - } -} - -#[api] -#[derive(Debug, Copy, Clone, Serialize, Deserialize, PartialEq, Eq)] -#[serde(rename_all = "kebab-case")] -pub enum APTRepositoryPackageType { - /// Debian package - Deb, - /// Debian source package - DebSrc, -} - -impl TryFrom<&str> for APTRepositoryPackageType { - type Error = Error; - - fn try_from(package_type: &str) -> Result { - match package_type { - "deb" => Ok(APTRepositoryPackageType::Deb), - "deb-src" => Ok(APTRepositoryPackageType::DebSrc), - _ => bail!("invalid package type '{package_type}'"), - } - } -} - -impl Display for APTRepositoryPackageType { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match self { - APTRepositoryPackageType::Deb => write!(f, "deb"), - APTRepositoryPackageType::DebSrc => write!(f, "deb-src"), - } - } -} - -#[api( - properties: { - Key: { - description: "Option key.", - type: String, - }, - Values: { - description: "Option values.", - type: Array, - items: { - description: "Value.", - type: String, - }, - }, - }, -)] -#[derive(Debug, Clone, Serialize, Deserialize)] -#[serde(rename_all = "PascalCase")] // for consistency -/// Additional options for an APT repository. -/// Used for both single- and mutli-value options. -pub struct APTRepositoryOption { - /// Option key. - pub key: String, - /// Option value(s). - pub values: Vec, -} - -#[api( - properties: { - Types: { - description: "List of package types.", - type: Array, - items: { - type: APTRepositoryPackageType, - }, - }, - URIs: { - description: "List of repository URIs.", - type: Array, - items: { - description: "Repository URI.", - type: String, - }, - }, - Suites: { - description: "List of distributions.", - type: Array, - items: { - description: "Package distribution.", - type: String, - }, - }, - Components: { - description: "List of repository components.", - type: Array, - items: { - description: "Repository component.", - type: String, - }, - }, - Options: { - type: Array, - optional: true, - items: { - type: APTRepositoryOption, - }, - }, - Comment: { - description: "Associated comment.", - type: String, - optional: true, - }, - FileType: { - type: APTRepositoryFileType, - }, - Enabled: { - description: "Whether the repository is enabled or not.", - type: Boolean, - }, - }, -)] -#[derive(Debug, Clone, Serialize, Deserialize)] -#[serde(rename_all = "PascalCase")] -/// Describes an APT repository. -pub struct APTRepository { - /// List of package types. - #[serde(default, skip_serializing_if = "Vec::is_empty")] - pub types: Vec, - - /// List of repository URIs. - #[serde(default, skip_serializing_if = "Vec::is_empty")] - #[serde(rename = "URIs")] - pub uris: Vec, - - /// List of package distributions. - #[serde(default, skip_serializing_if = "Vec::is_empty")] - pub suites: Vec, - - /// List of repository components. - #[serde(default, skip_serializing_if = "Vec::is_empty")] - pub components: Vec, - - /// Additional options. - #[serde(default, skip_serializing_if = "Vec::is_empty")] - pub options: Vec, - - /// Associated comment. - #[serde(default, skip_serializing_if = "String::is_empty")] - pub comment: String, - - /// Format of the defining file. - pub file_type: APTRepositoryFileType, - - /// Whether the repository is enabled or not. - pub enabled: bool, -} +use proxmox_apt_api_types::{ + APTRepository, APTRepositoryFileType, APTRepositoryHandle, APTRepositoryOption, +}; pub trait APTRepositoryImpl { /// Crates an empty repository. diff --git a/proxmox-apt/src/repositories/standard.rs b/proxmox-apt/src/repositories/standard.rs index 7858fac4..64fdea2a 100644 --- a/proxmox-apt/src/repositories/standard.rs +++ b/proxmox-apt/src/repositories/standard.rs @@ -1,70 +1,14 @@ -use std::fmt::Display; - -use anyhow::{bail, Error}; -use serde::{Deserialize, Serialize}; - -use crate::repositories::repository::{ - APTRepository, APTRepositoryFileType, APTRepositoryPackageType, +use proxmox_apt_api_types::{ + APTRepository, APTRepositoryFileType, APTRepositoryHandle, APTRepositoryPackageType, + APTStandardRepository, }; -use proxmox_schema::api; - -#[api( - properties: { - handle: { - description: "Handle referencing a standard repository.", - type: String, - }, - }, -)] -#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)] -#[serde(rename_all = "kebab-case")] -/// Reference to a standard repository and configuration status. -pub struct APTStandardRepository { - /// Handle referencing a standard repository. - pub handle: APTRepositoryHandle, - - /// Configuration status of the associated repository, where `None` means - /// not configured, and `Some(bool)` indicates enabled or disabled. - #[serde(skip_serializing_if = "Option::is_none")] - pub status: Option, - - /// Display name of the repository. - pub name: String, - - /// Description of the repository. - pub description: String, -} - -#[api] -#[derive(Debug, Copy, Clone, Serialize, Deserialize, PartialEq, Eq)] -#[serde(rename_all = "kebab-case")] -/// Handles for Proxmox repositories. -pub enum APTRepositoryHandle { - /// The enterprise repository for production use. - Enterprise, - /// The repository that can be used without subscription. - NoSubscription, - /// The test repository. - Test, - /// Ceph Quincy enterprise repository. - CephQuincyEnterprise, - /// Ceph Quincy no-subscription repository. - CephQuincyNoSubscription, - /// Ceph Quincy test repository. - CephQuincyTest, - // TODO: Add separate enum for ceph releases and use something like - // `CephTest(CephReleaseCodename),` once the API macro supports it. - /// Ceph Reef enterprise repository. - CephReefEnterprise, - /// Ceph Reef no-subscription repository. - CephReefNoSubscription, - /// Ceph Reef test repository. - CephReefTest, +pub trait APTStandardRepositoryImpl { + fn from_handle(handle: APTRepositoryHandle) -> APTStandardRepository; } -impl From for APTStandardRepository { - fn from(handle: APTRepositoryHandle) -> Self { +impl APTStandardRepositoryImpl for APTStandardRepository { + fn from_handle(handle: APTRepositoryHandle) -> APTStandardRepository { APTStandardRepository { handle, status: None, @@ -74,43 +18,6 @@ impl From for APTStandardRepository { } } -impl TryFrom<&str> for APTRepositoryHandle { - type Error = Error; - - fn try_from(string: &str) -> Result { - match string { - "enterprise" => Ok(APTRepositoryHandle::Enterprise), - "no-subscription" => Ok(APTRepositoryHandle::NoSubscription), - "test" => Ok(APTRepositoryHandle::Test), - "ceph-quincy-enterprise" => Ok(APTRepositoryHandle::CephQuincyEnterprise), - "ceph-quincy-no-subscription" => Ok(APTRepositoryHandle::CephQuincyNoSubscription), - "ceph-quincy-test" => Ok(APTRepositoryHandle::CephQuincyTest), - "ceph-reef-enterprise" => Ok(APTRepositoryHandle::CephReefEnterprise), - "ceph-reef-no-subscription" => Ok(APTRepositoryHandle::CephReefNoSubscription), - "ceph-reef-test" => Ok(APTRepositoryHandle::CephReefTest), - _ => bail!("unknown repository handle '{}'", string), - } - } -} - -impl Display for APTRepositoryHandle { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match self { - APTRepositoryHandle::Enterprise => write!(f, "enterprise"), - APTRepositoryHandle::NoSubscription => write!(f, "no-subscription"), - APTRepositoryHandle::Test => write!(f, "test"), - APTRepositoryHandle::CephQuincyEnterprise => write!(f, "ceph-quincy-enterprise"), - APTRepositoryHandle::CephQuincyNoSubscription => { - write!(f, "ceph-quincy-no-subscription") - } - APTRepositoryHandle::CephQuincyTest => write!(f, "ceph-quincy-test"), - APTRepositoryHandle::CephReefEnterprise => write!(f, "ceph-reef-enterprise"), - APTRepositoryHandle::CephReefNoSubscription => write!(f, "ceph-reef-no-subscription"), - APTRepositoryHandle::CephReefTest => write!(f, "ceph-reef-test"), - } - } -} - pub trait APTRepositoryHandleImpl { /// Get the description for the repository. fn description(self) -> String; diff --git a/proxmox-apt/tests/repositories.rs b/proxmox-apt/tests/repositories.rs index 37d665bf..228ef696 100644 --- a/proxmox-apt/tests/repositories.rs +++ b/proxmox-apt/tests/repositories.rs @@ -9,7 +9,7 @@ use proxmox_apt::repositories::{ APTRepositoryHandle, APTRepositoryInfo, APTStandardRepository, DebianCodename, }; use proxmox_apt::repositories::{ - APTRepositoryFileImpl, APTRepositoryHandleImpl, APTRepositoryImpl, + APTRepositoryFileImpl, APTRepositoryHandleImpl, APTRepositoryImpl, APTStandardRepositoryImpl, }; fn create_clean_directory(path: &PathBuf) -> Result<(), Error> { @@ -114,7 +114,7 @@ fn test_digest() -> Result<(), Error> { let new_path = write_dir.join(path.file_name().unwrap()); file.path = Some(new_path.clone().into_os_string().into_string().unwrap()); - let old_digest = file.digest.unwrap(); + let old_digest = file.digest.clone().unwrap(); // file does not exist yet... assert!(file.read_with_digest().is_err()); @@ -132,7 +132,7 @@ fn test_digest() -> Result<(), Error> { repo.enabled = !repo.enabled; // ...then it should work - file.digest = Some(old_digest); + file.digest = Some(old_digest.clone()); file.write()?; // expect a different digest, because the repo was modified @@ -361,15 +361,15 @@ fn test_standard_repositories() -> Result<(), Error> { let read_dir = test_dir.join("sources.list.d"); let mut expected = vec![ - APTStandardRepository::from(APTRepositoryHandle::Enterprise), - APTStandardRepository::from(APTRepositoryHandle::NoSubscription), - APTStandardRepository::from(APTRepositoryHandle::Test), - APTStandardRepository::from(APTRepositoryHandle::CephQuincyEnterprise), - APTStandardRepository::from(APTRepositoryHandle::CephQuincyNoSubscription), - APTStandardRepository::from(APTRepositoryHandle::CephQuincyTest), - APTStandardRepository::from(APTRepositoryHandle::CephReefEnterprise), - APTStandardRepository::from(APTRepositoryHandle::CephReefNoSubscription), - APTStandardRepository::from(APTRepositoryHandle::CephReefTest), + APTStandardRepository::from_handle(APTRepositoryHandle::Enterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::NoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::Test), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyEnterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyNoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::CephQuincyTest), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefEnterprise), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefNoSubscription), + APTStandardRepository::from_handle(APTRepositoryHandle::CephReefTest), ]; let absolute_suite_list = read_dir.join("absolute_suite.list"); -- 2.39.2 _______________________________________________ pbs-devel mailing list pbs-devel@lists.proxmox.com https://lists.proxmox.com/cgi-bin/mailman/listinfo/pbs-devel