[pdm-devel] [PATCH proxmox v2 05/14] installer-types: add common types used by the installer

Lukas Wagner l.wagner at proxmox.com
Tue Dec 9 10:35:12 CET 2025


Some notes inline.

On Fri Dec 5, 2025 at 12:25 PM CET, Christoph Heiss wrote:
> These moves common type definitions used throughout in the installer in
> it's own crate, so they can be re-used in other places.
>
> Some types are also renamed to improve clarity:
>
> - `NetdevWithMac` -> `NetworkInterface`
> - `SysInfo` -> `SystemInfo`
>
> Signed-off-by: Christoph Heiss <c.heiss at proxmox.com>
> ---
> Changes v1 -> v2:
>   * no changes
>
>  Cargo.toml                                   |   1 +
>  proxmox-installer-types/Cargo.toml           |  21 +++
>  proxmox-installer-types/debian/changelog     |   5 +
>  proxmox-installer-types/debian/control       |  44 ++++++
>  proxmox-installer-types/debian/debcargo.toml |   7 +
>  proxmox-installer-types/src/lib.rs           | 143 +++++++++++++++++++
>  6 files changed, 221 insertions(+)
>  create mode 100644 proxmox-installer-types/Cargo.toml
>  create mode 100644 proxmox-installer-types/debian/changelog
>  create mode 100644 proxmox-installer-types/debian/control
>  create mode 100644 proxmox-installer-types/debian/debcargo.toml
>  create mode 100644 proxmox-installer-types/src/lib.rs
>
> diff --git a/Cargo.toml b/Cargo.toml
> index 27a69afa..2df50903 100644
> --- a/Cargo.toml
> +++ b/Cargo.toml
> @@ -21,6 +21,7 @@ members = [
>      "proxmox-http",
>      "proxmox-http-error",
>      "proxmox-human-byte",
> +    "proxmox-installer-types",
>      "proxmox-io",
>      "proxmox-lang",
>      "proxmox-ldap",
> diff --git a/proxmox-installer-types/Cargo.toml b/proxmox-installer-types/Cargo.toml
> new file mode 100644
> index 00000000..62df7f4e
> --- /dev/null
> +++ b/proxmox-installer-types/Cargo.toml
> @@ -0,0 +1,21 @@
> +[package]
> +name = "proxmox-installer-types"
> +description = "Type definitions used within the installer"
> +version = "0.1.0"
> +
> +authors.workspace = true
> +edition.workspace = true
> +license.workspace = true
> +repository.workspace = true
> +homepage.workspace = true
> +exclude.workspace = true
> +rust-version.workspace = true
> +
> +[dependencies]
> +serde = { workspace = true, features = ["derive"] }
> +serde_plain.workspace = true
> +proxmox-network-types.workspace = true
> +
> +[features]
> +default = []
> +legacy = []
> diff --git a/proxmox-installer-types/debian/changelog b/proxmox-installer-types/debian/changelog
> new file mode 100644
> index 00000000..d2415aa0
> --- /dev/null
> +++ b/proxmox-installer-types/debian/changelog
> @@ -0,0 +1,5 @@
> +rust-proxmox-installer-types (0.1.0-1) unstable; urgency=medium
> +
> +  * Initial release.
> +
> + -- Proxmox Support Team <support at proxmox.com>  Tue, 25 Nov 2025 10:23:32 +0200
> diff --git a/proxmox-installer-types/debian/control b/proxmox-installer-types/debian/control
> new file mode 100644
> index 00000000..902977af
> --- /dev/null
> +++ b/proxmox-installer-types/debian/control
> @@ -0,0 +1,44 @@
> +Source: rust-proxmox-installer-types
> +Section: rust
> +Priority: optional
> +Build-Depends: debhelper-compat (= 13),
> + dh-sequence-cargo
> +Build-Depends-Arch: cargo:native <!nocheck>,
> + rustc:native (>= 1.82) <!nocheck>,
> + libstd-rust-dev <!nocheck>,
> + librust-proxmox-network-types-0.1+api-types-dev <!nocheck>,
> + librust-proxmox-network-types-0.1+default-dev <!nocheck>,
> + librust-serde-1+default-dev <!nocheck>,
> + librust-serde-1+derive-dev <!nocheck>,
> + librust-serde-plain-1+default-dev <!nocheck>
> +Maintainer: Proxmox Support Team <support at proxmox.com>
> +Standards-Version: 4.7.2
> +Vcs-Git: git://git.proxmox.com/git/proxmox.git
> +Vcs-Browser: https://git.proxmox.com/?p=proxmox.git
> +Homepage: https://proxmox.com
> +X-Cargo-Crate: proxmox-installer-types
> +
> +Package: librust-proxmox-installer-types-dev
> +Architecture: any
> +Multi-Arch: same
> +Depends:
> + ${misc:Depends},
> + librust-proxmox-network-types-0.1+api-types-dev,
> + librust-proxmox-network-types-0.1+default-dev,
> + librust-serde-1+default-dev,
> + librust-serde-1+derive-dev,
> + librust-serde-plain-1+default-dev
> +Provides:
> + librust-proxmox-installer-types+default-dev (= ${binary:Version}),
> + librust-proxmox-installer-types+legacy-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0+default-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0+legacy-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1+default-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1+legacy-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1.0-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1.0+default-dev (= ${binary:Version}),
> + librust-proxmox-installer-types-0.1.0+legacy-dev (= ${binary:Version})
> +Description: Type definitions used within the installer - Rust source code
> + Source code for Debianized Rust crate "proxmox-installer-types"
> diff --git a/proxmox-installer-types/debian/debcargo.toml b/proxmox-installer-types/debian/debcargo.toml
> new file mode 100644
> index 00000000..b7864cdb
> --- /dev/null
> +++ b/proxmox-installer-types/debian/debcargo.toml
> @@ -0,0 +1,7 @@
> +overlay = "."
> +crate_src_path = ".."
> +maintainer = "Proxmox Support Team <support at proxmox.com>"
> +
> +[source]
> +vcs_git = "git://git.proxmox.com/git/proxmox.git"
> +vcs_browser = "https://git.proxmox.com/?p=proxmox.git"
> diff --git a/proxmox-installer-types/src/lib.rs b/proxmox-installer-types/src/lib.rs
> new file mode 100644
> index 00000000..07927cb0
> --- /dev/null
> +++ b/proxmox-installer-types/src/lib.rs
> @@ -0,0 +1,143 @@
> +//! Defines API types used within the installer, primarily for interacting
> +//! with proxmox-auto-installer.
> +//!
> +//! [`BTreeMap`]s are used to store certain properties to keep the order of
> +//! them stable, compared to storing them in an ordinary [`HashMap`].
> +
> +#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))]
> +#![deny(unsafe_code, missing_docs)]
> +
> +use serde::{Deserialize, Serialize};
> +use std::{
> +    collections::{BTreeMap, HashMap},
> +    fmt::{self, Display},
> +};
> +
> +use proxmox_network_types::mac_address::MacAddress;
> +
> +/// Default placeholder value for the administrator email address.
> +pub const EMAIL_DEFAULT_PLACEHOLDER: &str = "mail at example.invalid";
> +
> +#[derive(Copy, Clone, Eq, Deserialize, PartialEq, Serialize)]
> +#[serde(rename_all = "lowercase")]
> +/// Whether the system boots using legacy BIOS or (U)EFI.
> +pub enum BootType {
> +    /// System boots using legacy BIOS.
> +    Bios,
> +    /// System boots using (U)EFI.
> +    Efi,
> +}

We already have some very similar definitions in proxmox-node-status -
not sure how easy it would be to consolidate the two types, since the
serialized form might not be exactly the same. Maybe the installer could
just use custom de/serializers and reuse the types from
proxmox-node-status?

> +
> +/// Uses a BTreeMap to have the keys sorted
> +pub type UdevProperties = BTreeMap<String, String>;
> +
> +#[derive(Clone, Deserialize, Debug)]
> +/// Information extracted from udev about devices present in the system.
> +pub struct UdevInfo {
> +    /// udev information for each disk.
> +    pub disks: BTreeMap<String, UdevProperties>,
> +    /// udev information for each network interface card.
> +    pub nics: BTreeMap<String, UdevProperties>,
> +}
> +
> +#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
> +/// Information about the hardware and installer in use.
> +pub struct SystemInfo {
> +    /// Information about the product to be installed.
> +    pub product: ProductConfig,
> +    /// Information about the ISO.
> +    pub iso: IsoInfo,
> +    /// Raw DMI information of the system.
> +    pub dmi: SystemDMI,
> +    /// Network devices present on the system.
> +    pub network_interfaces: Vec<NetworkInterface>,
> +}
> +
> +#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
> +/// The per-product configuration of the installer.
> +pub struct ProductConfig {
> +    /// Full name of the product.
> +    pub fullname: String,
> +    /// The actual product the installer is for.
> +    pub product: ProxmoxProduct,
> +    /// Whether to enable installations on Btrfs.
> +    pub enable_btrfs: bool,
> +}
> +
> +impl ProductConfig {
> +    /// A mocked ProductConfig simulating a Proxmox VE environment.
> +    pub fn mocked() -> Self {
> +        Self {
> +            fullname: String::from("Proxmox VE (mocked)"),
> +            product: ProxmoxProduct::PVE,
> +            enable_btrfs: true,
> +        }
> +    }
> +}
> +
> +#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
> +/// Information about the ISO itself.
> +pub struct IsoInfo {
> +    /// Version of the product.
> +    pub release: String,
> +    /// Version of the ISO itself, e.g. the spin.
> +    pub isorelease: String,
> +}
> +
> +impl IsoInfo {
> +    /// A mocked IsoInfo with some edge case to convey that this is not necessarily purely numeric.
> +    pub fn mocked() -> Self {
> +        Self {
> +            release: String::from("42.1"),
> +            isorelease: String::from("mocked-1"),
> +        }
> +    }
> +}
> +
> +#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
> +/// Collection of various DMI information categories.
> +pub struct SystemDMI {
> +    /// Information about the system baseboard.
> +    pub baseboard: HashMap<String, String>,
> +    /// Information about the system chassis.
> +    pub chassis: HashMap<String, String>,
> +    /// Information about the hardware itself, mostly identifiers.
> +    pub system: HashMap<String, String>,
> +}
> +
> +#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
> +/// A unique network interface.
> +pub struct NetworkInterface {
> +    /// The network link name
> +    pub link: String,
> +    /// The MAC address of the network device
> +    pub mac: MacAddress,
> +}
> +
> +#[allow(clippy::upper_case_acronyms)]
> +#[derive(Debug, Clone, Copy, Deserialize, PartialEq, Serialize)]
> +#[serde(rename_all = "lowercase")]
> +/// The name of the product.
> +pub enum ProxmoxProduct {
> +    /// Proxmox Virtual Environment
> +    PVE,
> +    /// Proxmox Backup Server
> +    PBS,
> +    /// Proxmox Mail Gateway
> +    PMG,
> +    /// Proxmox Datacenter Manager
> +    PDM,
> +}

I think we generally prefer regular UpperPascalCase, even for acronyms,
as per the official Rust naming guide [1].
So these should rather be Pve, Pbs, etc.

[1] https://rust-lang.github.io/api-guidelines/naming.html

> +
> +serde_plain::derive_fromstr_from_deserialize!(ProxmoxProduct);
> +
> +impl Display for ProxmoxProduct {
> +    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
> +        match self {
> +            Self::PVE => write!(f, "Proxmox Virtualization Environment"),

Virtual Environment, not Virtualization Environment :)

> +            Self::PBS => write!(f, "Proxmox Backup Server"),
> +            Self::PMG => write!(f, "Proxmox Mail Gateway"),
> +            Self::PDM => write!(f, "Proxmox Datacenter Manager"),
> +        }
> +    }
> +}





More information about the pdm-devel mailing list