public inbox for pve-devel@lists.proxmox.com
 help / color / mirror / Atom feed
* [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes
@ 2026-04-13 12:10 Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox 1/7] pbs-api-types: add InstanceId response type Lukas Wagner
                   ` (6 more replies)
  0 siblings, 7 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

In PDM we require some way to match PBS storage <-> PBS remote.

Having some kind of unique ID for each PBS instance should make it quite easy
to establish such a mapping completely automatically.

The general approach would be
  1.) add /nodes/localhost/instance-id route in PBS, returning a unique, per-installation ID
  2.) add something like /nodes/.../storage/<id>/instance-id in PVE, which uses
    proxmox-backup-client internally to return the instance ID for this PBS storage
  3.) PDM can then use both API routes to establish the mapping


proxmox:

Fabian Grünbichler (1):
  systemd: add support for machine-id generation

Lukas Wagner (1):
  pbs-api-types: add InstanceId response type

 pbs-api-types/src/node.rs       |  9 +++++
 proxmox-systemd/src/lib.rs      |  2 +
 proxmox-systemd/src/sd_id128.rs | 70 +++++++++++++++++++++++++++++++++
 proxmox-systemd/src/sys.rs      |  6 +++
 4 files changed, 87 insertions(+)
 create mode 100644 proxmox-systemd/src/sd_id128.rs


proxmox-backup:

Lukas Wagner (3):
  api: add /nodes/localhost/instance-id
  client: add 'instance-id' sub-command
  manager: add instance-id subcommand

 proxmox-backup-client/src/main.rs      | 41 ++++++++++++++++++++++++--
 src/api2/node/mod.rs                   | 41 +++++++++++++++++++++++++-
 src/bin/proxmox_backup_manager/node.rs | 27 +++++++++++++++++
 3 files changed, 106 insertions(+), 3 deletions(-)


pve-common:

Lukas Wagner (1):
  pbs-client: add support for the 'instance id' command

 src/PVE/PBSClient.pm | 7 +++++++
 1 file changed, 7 insertions(+)


pve-storage:

Lukas Wagner (1):
  api: add /nodes/<node>/storage/<storage>/instance-id route

 src/PVE/API2/Storage/Status.pm | 50 +++++++++++++++++++++++++++++++++-
 1 file changed, 49 insertions(+), 1 deletion(-)


Summary over all repositories:
  9 files changed, 249 insertions(+), 4 deletions(-)

-- 
Generated by murpp 0.11.0




^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH proxmox 1/7] pbs-api-types: add InstanceId response type
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox 2/7] systemd: add support for machine-id generation Lukas Wagner
                   ` (5 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

This type will be used to uniquely identify a PBS node, which comes in
useful to match PBS storages to PBS remotes in PDM.

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---
 pbs-api-types/src/node.rs | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/pbs-api-types/src/node.rs b/pbs-api-types/src/node.rs
index da3e4118..c799abc0 100644
--- a/pbs-api-types/src/node.rs
+++ b/pbs-api-types/src/node.rs
@@ -453,3 +453,12 @@ impl Iterator for AcmeDomainIter<'_> {
         )
     }
 }
+
+#[api]
+#[derive(Serialize, Deserialize, Clone, PartialEq, Debug)]
+#[serde(rename_all = "kebab-case")]
+/// Unique instance identity information.
+pub struct InstanceId {
+    /// Unique instance identifier.
+    pub instance_id: String,
+}
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH proxmox 2/7] systemd: add support for machine-id generation
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox 1/7] pbs-api-types: add InstanceId response type Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox-backup 3/7] api: add /nodes/localhost/instance-id Lukas Wagner
                   ` (4 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

From: Fabian Grünbichler <f.gruenbichler@proxmox.com>

the plain machine-id should not be leaked to external systems, but libsystemd
provides helpers for deriving application-id based identifiers that are useful
for identifying a machine externally.

Signed-off-by: Fabian Grünbichler <f.gruenbichler@proxmox.com>
---
 proxmox-systemd/src/lib.rs      |  2 +
 proxmox-systemd/src/sd_id128.rs | 70 +++++++++++++++++++++++++++++++++
 proxmox-systemd/src/sys.rs      |  6 +++
 3 files changed, 78 insertions(+)
 create mode 100644 proxmox-systemd/src/sd_id128.rs

diff --git a/proxmox-systemd/src/lib.rs b/proxmox-systemd/src/lib.rs
index 456d88c3..f79c204c 100644
--- a/proxmox-systemd/src/lib.rs
+++ b/proxmox-systemd/src/lib.rs
@@ -7,3 +7,5 @@ pub use escape::{escape_unit, unescape_unit, unescape_unit_path, UnescapeError};
 
 pub mod journal;
 pub mod notify;
+
+pub mod sd_id128;
diff --git a/proxmox-systemd/src/sd_id128.rs b/proxmox-systemd/src/sd_id128.rs
new file mode 100644
index 00000000..a98a6663
--- /dev/null
+++ b/proxmox-systemd/src/sd_id128.rs
@@ -0,0 +1,70 @@
+use std::fmt;
+
+use crate::sys::{self, sd_id128_t};
+
+#[derive(Debug, PartialEq, Eq)]
+pub enum SystemdId128Error {
+    InvalidAppId,
+    GenerationError,
+}
+
+impl std::error::Error for SystemdId128Error {
+    fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
+        None
+    }
+}
+
+impl fmt::Display for SystemdId128Error {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        match self {
+            SystemdId128Error::InvalidAppId => f.write_str("Provided application ID is invalid."),
+            SystemdId128Error::GenerationError => {
+                f.write_str("Failed to generate machine-id based on application ID.")
+            }
+        }
+    }
+}
+
+pub fn get_app_specific_id(app_id: [u8; 16]) -> Result<[u8; 16], SystemdId128Error> {
+    let mut res = sd_id128_t { bytes: [0; 16] };
+
+    if app_id.iter().all(|b| *b == 0) {
+        return Err(SystemdId128Error::InvalidAppId);
+    }
+    unsafe {
+        sys::sd_id128_get_machine_app_specific(sd_id128_t { bytes: app_id }, &mut res);
+    }
+    if res.bytes.iter().all(|b| *b == 0) {
+        return Err(SystemdId128Error::GenerationError);
+    }
+    Ok(res.bytes)
+}
+
+#[test]
+fn test_invalid_app_id() {
+    let invalid = [0; 16];
+    let res = get_app_specific_id(invalid);
+    assert!(res.is_err());
+    assert_eq!(res, Err(SystemdId128Error::InvalidAppId));
+}
+
+#[test]
+fn test_valid_app_id() {
+    // no machine-id, no app-specific ID either..
+    if !std::path::Path::new("/etc/machine-id").exists() {
+        return;
+    }
+
+    // UUID generated with `systemd-id128 new` and converted from hex
+    let valid = 950247666410175165299169499632875718_u128.to_le_bytes();
+
+    let res = get_app_specific_id(valid);
+    assert!(res.is_ok());
+
+    let res2 = get_app_specific_id(valid);
+    assert!(res2.is_ok());
+
+    // cannot verify the expected result, since that depends on the machine the test runs on
+    // we can verify that two generations using the same machine and app-id give identical results
+    assert_eq!(res, res2);
+}
diff --git a/proxmox-systemd/src/sys.rs b/proxmox-systemd/src/sys.rs
index eabd44d1..ea2b6061 100644
--- a/proxmox-systemd/src/sys.rs
+++ b/proxmox-systemd/src/sys.rs
@@ -4,6 +4,11 @@ use std::os::fd::RawFd;
 
 pub const LISTEN_FDS_START: RawFd = 3;
 
+#[repr(C)]
+pub struct sd_id128_t {
+    pub bytes: [u8; 16],
+}
+
 #[link(name = "systemd")]
 unsafe extern "C" {
     pub fn sd_journal_stream_fd(
@@ -24,6 +29,7 @@ unsafe extern "C" {
         unset_environment: c_int,
         names: *mut *mut *mut c_char,
     ) -> c_int;
+    pub fn sd_id128_get_machine_app_specific(app_id: sd_id128_t, ret: *mut sd_id128_t) -> c_int;
 }
 
 pub fn check_call(ret: c_int) -> Result<c_int, io::Error> {
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH proxmox-backup 3/7] api: add /nodes/localhost/instance-id
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox 1/7] pbs-api-types: add InstanceId response type Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox 2/7] systemd: add support for machine-id generation Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 12:10 ` [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command Lukas Wagner
                   ` (3 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

This one returns a unique ID that can be used to uniquely identify a PBS
node. This will be used by PDM to match PBS storages in a PVE cluster to
PBS remotes in PDM, mainly for associating backup jobs with the
appropriate PBS remote. Later we can also use this to match PBS sync
jobs to their matching PBS remotes in PDM.

The instance ID is derived from /etc/machine-id as recommended by
systemd [1] by using proxmox_systemd::sd_id128::get_app_specific_id.

[1] https://www.freedesktop.org/software/systemd/man/latest/sd_id128_get_machine_app_specific.html

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---
 src/api2/node/mod.rs | 41 ++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 40 insertions(+), 1 deletion(-)

diff --git a/src/api2/node/mod.rs b/src/api2/node/mod.rs
index 42e1dbaa2..93770c4f5 100644
--- a/src/api2/node/mod.rs
+++ b/src/api2/node/mod.rs
@@ -25,7 +25,7 @@ use proxmox_schema::*;
 use proxmox_sortable_macro::sortable;
 use proxmox_sys::fd::fd_change_cloexec;
 
-use pbs_api_types::{NodeShellTicket, NODE_SCHEMA, PRIV_SYS_CONSOLE};
+use pbs_api_types::{InstanceId, NodeShellTicket, NODE_SCHEMA, PRIV_SYS_CONSOLE};
 use tracing::{info, warn};
 
 use crate::auth::{private_auth_keyring, public_auth_keyring};
@@ -291,12 +291,51 @@ fn list_nodes() -> Result<Value, Error> {
     Ok(json!([ { "node": proxmox_sys::nodename().to_string() } ]))
 }
 
+///  Static key used for deriving a unique instance id from `/etc/machine-id` using
+///  [`proxmox_systemd::sd_id128::get_app_specific_id`].
+///
+///  This key was generated `systemd-id128 new`.
+///
+const INSTANCE_ID_KEY: [u8; 16] = 0xe5415d9999c146399b8bdae1260e19d2_u128.to_le_bytes();
+
+#[api(
+    protected: false,
+    input: {
+        properties: {
+            node: {
+                schema: NODE_SCHEMA,
+                optional: true,
+            },
+        }
+    },
+    returns: {
+        type: InstanceId,
+    },
+    access: {
+        permission: &Permission::Anybody,
+    }
+)]
+/// Returns a unique ID for this PBS node. The ID is derived from `/etc/machine-id`.
+pub fn get_instance_id() -> Result<InstanceId, Error> {
+    let machine_id_derived_app_id =
+        proxmox_systemd::sd_id128::get_app_specific_id(INSTANCE_ID_KEY)?;
+    let machine_id_derived_app_id = hex::encode(machine_id_derived_app_id);
+
+    Ok(InstanceId {
+        instance_id: machine_id_derived_app_id,
+    })
+}
+
 pub const SUBDIRS: SubdirMap = &[
     ("apt", &apt::ROUTER),
     ("certificates", &certificates::ROUTER),
     ("config", &config::ROUTER),
     ("disks", &disks::ROUTER),
     ("dns", &dns::ROUTER),
+    (
+        "instance-id",
+        &Router::new().get(&API_METHOD_GET_INSTANCE_ID),
+    ),
     ("journal", &journal::ROUTER),
     ("network", &network::ROUTER),
     ("report", &report::ROUTER),
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
                   ` (2 preceding siblings ...)
  2026-04-13 12:10 ` [PATCH proxmox-backup 3/7] api: add /nodes/localhost/instance-id Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 13:26   ` Shannon Sterz
  2026-04-13 12:10 ` [PATCH proxmox-backup 5/7] manager: add instance-id subcommand Lukas Wagner
                   ` (2 subsequent siblings)
  6 siblings, 1 reply; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

This allows users to query the instance-id from the
proxmox-backup-client tool. This will also be used by the PBS client in
PVE to lookup the instance-id from a yet to be introduced API endpoint
that returns the instance-id for a given PBS storage.

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---
 proxmox-backup-client/src/main.rs | 41 +++++++++++++++++++++++++++++--
 1 file changed, 39 insertions(+), 2 deletions(-)

diff --git a/proxmox-backup-client/src/main.rs b/proxmox-backup-client/src/main.rs
index 2ada87bdd..9f4a82e26 100644
--- a/proxmox-backup-client/src/main.rs
+++ b/proxmox-backup-client/src/main.rs
@@ -25,8 +25,8 @@ use pxar::accessor::{MaybeReady, ReadAt, ReadAtOperation};
 
 use pbs_api_types::{
     ArchiveType, Authid, BackupArchiveName, BackupDir, BackupGroup, BackupNamespace, BackupPart,
-    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, PathPattern,
-    PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
+    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, InstanceId,
+    PathPattern, PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
     BACKUP_ID_SCHEMA, BACKUP_NAMESPACE_SCHEMA, BACKUP_TIME_SCHEMA, BACKUP_TYPE_SCHEMA,
     CATALOG_NAME, ENCRYPTED_KEY_BLOB_NAME, MANIFEST_BLOB_NAME,
 };
@@ -139,6 +139,39 @@ fn record_repository(repo: &BackupRepository) {
     );
 }
 
+#[api(
+    input: {
+        properties: {
+            repository: {
+                schema: REPO_URL_SCHEMA,
+                optional: true,
+            },
+            "output-format": {
+                schema: OUTPUT_FORMAT,
+                optional: true,
+            },
+        },
+    },
+)]
+/// Start garbage collection for a specific repository.
+async fn get_instance_id(param: Value) -> Result<Value, Error> {
+    let repo = extract_repository_from_value(&param)?;
+    let output_format = get_output_format(&param);
+    let client = connect(&repo)?;
+
+    let path = format!("api2/json/nodes/localhost/instance-id");
+    let mut result = client.get(&path, None).await?;
+
+    let id: InstanceId = serde_json::from_value(result["data"].take())?;
+
+    if output_format == "text" {
+        println!("instance-id: {}", id.instance_id);
+    } else {
+        format_and_print_result(&id, &output_format);
+    }
+    Ok(Value::Null)
+}
+
 async fn api_datastore_list_snapshots(
     client: &HttpClient,
     store: &str,
@@ -2076,6 +2109,9 @@ fn main() {
     let version_cmd_def =
         CliCommand::new(&API_METHOD_API_VERSION).completion_cb("repository", complete_repository);
 
+    let instance_id_cmd_def = CliCommand::new(&API_METHOD_GET_INSTANCE_ID)
+        .completion_cb("repository", complete_repository);
+
     let change_owner_cmd_def = CliCommand::new(&API_METHOD_CHANGE_BACKUP_OWNER)
         .arg_param(&["group", "new-owner"])
         .completion_cb("ns", complete_namespace)
@@ -2086,6 +2122,7 @@ fn main() {
     let cmd_def = CliCommandMap::new()
         .insert("backup", backup_cmd_def)
         .insert("garbage-collect", garbage_collect_cmd_def)
+        .insert("instance-id", instance_id_cmd_def)
         .insert("list", list_cmd_def)
         .insert("login", login_cmd_def)
         .insert("logout", logout_cmd_def)
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH proxmox-backup 5/7] manager: add instance-id subcommand
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
                   ` (3 preceding siblings ...)
  2026-04-13 12:10 ` [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 13:26   ` Shannon Sterz
  2026-04-13 12:10 ` [PATCH common 6/7] pbs-client: add support for the 'instance id' command Lukas Wagner
  2026-04-13 12:10 ` [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route Lukas Wagner
  6 siblings, 1 reply; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

For the sake of completeness also allow to query the instance ID from
the proxmox-backup-manager admin tool.

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---
 src/bin/proxmox_backup_manager/node.rs | 27 ++++++++++++++++++++++++++
 1 file changed, 27 insertions(+)

diff --git a/src/bin/proxmox_backup_manager/node.rs b/src/bin/proxmox_backup_manager/node.rs
index 4da61690f..34c481587 100644
--- a/src/bin/proxmox_backup_manager/node.rs
+++ b/src/bin/proxmox_backup_manager/node.rs
@@ -32,9 +32,36 @@ fn get_node_config(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Valu
     Ok(Value::Null)
 }
 
+#[api(
+    input: {
+        properties: {
+            "output-format": {
+                schema: OUTPUT_FORMAT,
+                optional: true,
+            },
+        }
+    }
+)]
+/// Show node configuration
+fn get_instance_id(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Value, Error> {
+    let output_format = get_output_format(&param);
+
+    let info = &api2::node::API_METHOD_GET_INSTANCE_ID;
+    let mut data = match info.handler {
+        ApiHandler::Sync(handler) => (handler)(param, info, rpcenv)?,
+        _ => unreachable!(),
+    };
+
+    let options = default_table_format_options();
+    format_and_print_result_full(&mut data, &info.returns, &output_format, &options);
+
+    Ok(Value::Null)
+}
+
 pub fn node_commands() -> CommandLineInterface {
     let cmd_def = CliCommandMap::new()
         .insert("show", CliCommand::new(&API_METHOD_GET_NODE_CONFIG))
+        .insert("instance-id", CliCommand::new(&API_METHOD_GET_INSTANCE_ID))
         .insert(
             "update",
             CliCommand::new(&api2::node::config::API_METHOD_UPDATE_NODE_CONFIG)
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH common 6/7] pbs-client: add support for the 'instance id' command
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
                   ` (4 preceding siblings ...)
  2026-04-13 12:10 ` [PATCH proxmox-backup 5/7] manager: add instance-id subcommand Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 12:10 ` [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route Lukas Wagner
  6 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

This allows us to retrieve a unique instance identifier for a PBS
server.

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---
 src/PVE/PBSClient.pm | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/src/PVE/PBSClient.pm b/src/PVE/PBSClient.pm
index 6333304..b1c16f2 100644
--- a/src/PVE/PBSClient.pm
+++ b/src/PVE/PBSClient.pm
@@ -257,6 +257,13 @@ my sub split_namespaced_parameter : prototype($$) {
     return ($namespace, $snapshot);
 }
 
+# Get the instance identifier for this backup server.
+sub get_instance_id {
+    my ($self) = @_;
+
+    return run_client_cmd($self, "instance-id");
+}
+
 # lists all snapshots, optionally limited to a specific group
 sub get_snapshots {
     my ($self, $group) = @_;
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route
  2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
                   ` (5 preceding siblings ...)
  2026-04-13 12:10 ` [PATCH common 6/7] pbs-client: add support for the 'instance id' command Lukas Wagner
@ 2026-04-13 12:10 ` Lukas Wagner
  2026-04-13 13:26   ` Shannon Sterz
  6 siblings, 1 reply; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 12:10 UTC (permalink / raw)
  To: pbs-devel, pve-devel

This API allows us to retrieve the instance ID of PBS storages. This is
useful to establish a mapping between PBS storage and PBS remotes in
PDM.

Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
---

Notes:
    Maybe we want to make this more general and just call it /id or
    something, in case we want to use a similar mechanism for other storage
    types as well?
    
    Also could make sense to cache the response.

 src/PVE/API2/Storage/Status.pm | 50 +++++++++++++++++++++++++++++++++-
 1 file changed, 49 insertions(+), 1 deletion(-)

diff --git a/src/PVE/API2/Storage/Status.pm b/src/PVE/API2/Storage/Status.pm
index 8225c3a..52aa673 100644
--- a/src/PVE/API2/Storage/Status.pm
+++ b/src/PVE/API2/Storage/Status.pm
@@ -14,7 +14,7 @@ use PVE::JSONSchema qw(get_standard_option);
 use PVE::RESTHandler;
 use PVE::RPCEnvironment;
 use PVE::RRD;
-use PVE::Tools qw(run_command);
+use PVE::Tools qw(run_command extract_param);
 
 use PVE::API2::Storage::Content;
 use PVE::API2::Storage::FileRestore;
@@ -308,6 +308,7 @@ __PACKAGE__->register_method({
             { subdir => 'download-url' },
             { subdir => 'file-restore' },
             { subdir => 'import-metadata' },
+            { subdir => 'instance-id' },
             { subdir => 'oci-registry-pull' },
             { subdir => 'prunebackups' },
             { subdir => 'rrd' },
@@ -1118,4 +1119,51 @@ __PACKAGE__->register_method({
     },
 });
 
+__PACKAGE__->register_method({
+    name => 'instance_id',
+    path => '{storage}/instance-id',
+    method => 'GET',
+    description => "Return unique storage instance ID (PBS only)",
+    permissions => {
+        check => ['perm', '/storage/{storage}', ['Datastore.Audit']],
+    },
+    protected => 1,
+    proxyto => 'node',
+    parameters => {
+        additionalProperties => 0,
+        properties => {
+            node => get_standard_option('pve-node'),
+            storage => get_standard_option('pve-storage-id'),
+        },
+    },
+    returns => {
+        type => "object",
+        properties => {
+            'instance-id' => {
+                type => 'string',
+                description => 'Unique instance ID',
+            },
+        },
+    },
+    code => sub {
+        my ($param) = @_;
+
+        my $rpcenv = PVE::RPCEnvironment::get();
+        my $user = $rpcenv->get_user();
+
+        my $storeid = extract_param($param, 'storage');
+
+        my $cfg = PVE::Storage::config();
+        my $scfg = PVE::Storage::storage_config($cfg, $storeid);
+
+        raise_param_exc({ 'storage' => "Only PBS storages supported." })
+            if $scfg->{type} ne 'pbs';
+
+        my $client = PVE::PBSClient->new($scfg, $storeid);
+        my $ret = $client->get_instance_id();
+
+        return $ret;
+    },
+});
+
 1;
-- 
2.47.3





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route
  2026-04-13 12:10 ` [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route Lukas Wagner
@ 2026-04-13 13:26   ` Shannon Sterz
  2026-04-13 13:37     ` Lukas Wagner
  0 siblings, 1 reply; 14+ messages in thread
From: Shannon Sterz @ 2026-04-13 13:26 UTC (permalink / raw)
  To: Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
> This API allows us to retrieve the instance ID of PBS storages. This is
> useful to establish a mapping between PBS storage and PBS remotes in
> PDM.
>
> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
> ---
>
> Notes:
>     Maybe we want to make this more general and just call it /id or
>     something, in case we want to use a similar mechanism for other storage
>     types as well?
>
>     Also could make sense to cache the response.
>
>  src/PVE/API2/Storage/Status.pm | 50 +++++++++++++++++++++++++++++++++-
>  1 file changed, 49 insertions(+), 1 deletion(-)
>
> diff --git a/src/PVE/API2/Storage/Status.pm b/src/PVE/API2/Storage/Status.pm
> index 8225c3a..52aa673 100644
> --- a/src/PVE/API2/Storage/Status.pm
> +++ b/src/PVE/API2/Storage/Status.pm
> @@ -14,7 +14,7 @@ use PVE::JSONSchema qw(get_standard_option);
>  use PVE::RESTHandler;
>  use PVE::RPCEnvironment;
>  use PVE::RRD;
> -use PVE::Tools qw(run_command);
> +use PVE::Tools qw(run_command extract_param);
>
>  use PVE::API2::Storage::Content;
>  use PVE::API2::Storage::FileRestore;
> @@ -308,6 +308,7 @@ __PACKAGE__->register_method({
>              { subdir => 'download-url' },
>              { subdir => 'file-restore' },
>              { subdir => 'import-metadata' },
> +            { subdir => 'instance-id' },
>              { subdir => 'oci-registry-pull' },
>              { subdir => 'prunebackups' },
>              { subdir => 'rrd' },
> @@ -1118,4 +1119,51 @@ __PACKAGE__->register_method({
>      },
>  });
>
> +__PACKAGE__->register_method({
> +    name => 'instance_id',
> +    path => '{storage}/instance-id',
> +    method => 'GET',
> +    description => "Return unique storage instance ID (PBS only)",
> +    permissions => {
> +        check => ['perm', '/storage/{storage}', ['Datastore.Audit']],
> +    },
> +    protected => 1,
> +    proxyto => 'node',
> +    parameters => {
> +        additionalProperties => 0,
> +        properties => {
> +            node => get_standard_option('pve-node'),
> +            storage => get_standard_option('pve-storage-id'),
> +        },
> +    },
> +    returns => {
> +        type => "object",
> +        properties => {
> +            'instance-id' => {
> +                type => 'string',
> +                description => 'Unique instance ID',
> +            },
> +        },
> +    },
> +    code => sub {
> +        my ($param) = @_;
> +
> +        my $rpcenv = PVE::RPCEnvironment::get();
> +        my $user = $rpcenv->get_user();

sorry if im missing something, but are these two lines a copy-paste
mistake or do you rely on a side-effect of `get_user()` here (i.e.
making sure that this function is called in an `RPCEnvironment` with a
set user)?

> +        my $storeid = extract_param($param, 'storage');
> +
> +        my $cfg = PVE::Storage::config();
> +        my $scfg = PVE::Storage::storage_config($cfg, $storeid);
> +
> +        raise_param_exc({ 'storage' => "Only PBS storages supported." })
> +            if $scfg->{type} ne 'pbs';
> +
> +        my $client = PVE::PBSClient->new($scfg, $storeid);
> +        my $ret = $client->get_instance_id();
> +
> +        return $ret;
> +    },
> +});
> +
>  1;





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH proxmox-backup 5/7] manager: add instance-id subcommand
  2026-04-13 12:10 ` [PATCH proxmox-backup 5/7] manager: add instance-id subcommand Lukas Wagner
@ 2026-04-13 13:26   ` Shannon Sterz
  2026-04-13 13:38     ` Lukas Wagner
  0 siblings, 1 reply; 14+ messages in thread
From: Shannon Sterz @ 2026-04-13 13:26 UTC (permalink / raw)
  To: Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
> For the sake of completeness also allow to query the instance ID from
> the proxmox-backup-manager admin tool.
>
> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
> ---
>  src/bin/proxmox_backup_manager/node.rs | 27 ++++++++++++++++++++++++++
>  1 file changed, 27 insertions(+)
>
> diff --git a/src/bin/proxmox_backup_manager/node.rs b/src/bin/proxmox_backup_manager/node.rs
> index 4da61690f..34c481587 100644
> --- a/src/bin/proxmox_backup_manager/node.rs
> +++ b/src/bin/proxmox_backup_manager/node.rs
> @@ -32,9 +32,36 @@ fn get_node_config(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Valu
>      Ok(Value::Null)
>  }
>
> +#[api(
> +    input: {
> +        properties: {
> +            "output-format": {
> +                schema: OUTPUT_FORMAT,
> +                optional: true,
> +            },
> +        }
> +    }
> +)]
> +/// Show node configuration

nit: this description should probably also be something like "Get the
instance ID of the current PBS instance." or similar.

> +fn get_instance_id(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Value, Error> {
> +    let output_format = get_output_format(&param);
> +
> +    let info = &api2::node::API_METHOD_GET_INSTANCE_ID;
> +    let mut data = match info.handler {
> +        ApiHandler::Sync(handler) => (handler)(param, info, rpcenv)?,
> +        _ => unreachable!(),
> +    };
> +
> +    let options = default_table_format_options();
> +    format_and_print_result_full(&mut data, &info.returns, &output_format, &options);
> +
> +    Ok(Value::Null)
> +}
> +
>  pub fn node_commands() -> CommandLineInterface {
>      let cmd_def = CliCommandMap::new()
>          .insert("show", CliCommand::new(&API_METHOD_GET_NODE_CONFIG))
> +        .insert("instance-id", CliCommand::new(&API_METHOD_GET_INSTANCE_ID))
>          .insert(
>              "update",
>              CliCommand::new(&api2::node::config::API_METHOD_UPDATE_NODE_CONFIG)





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command
  2026-04-13 12:10 ` [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command Lukas Wagner
@ 2026-04-13 13:26   ` Shannon Sterz
  2026-04-13 13:39     ` Lukas Wagner
  0 siblings, 1 reply; 14+ messages in thread
From: Shannon Sterz @ 2026-04-13 13:26 UTC (permalink / raw)
  To: Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
> This allows users to query the instance-id from the
> proxmox-backup-client tool. This will also be used by the PBS client in
> PVE to lookup the instance-id from a yet to be introduced API endpoint
> that returns the instance-id for a given PBS storage.
>
> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
> ---
>  proxmox-backup-client/src/main.rs | 41 +++++++++++++++++++++++++++++--
>  1 file changed, 39 insertions(+), 2 deletions(-)
>
> diff --git a/proxmox-backup-client/src/main.rs b/proxmox-backup-client/src/main.rs
> index 2ada87bdd..9f4a82e26 100644
> --- a/proxmox-backup-client/src/main.rs
> +++ b/proxmox-backup-client/src/main.rs
> @@ -25,8 +25,8 @@ use pxar::accessor::{MaybeReady, ReadAt, ReadAtOperation};
>
>  use pbs_api_types::{
>      ArchiveType, Authid, BackupArchiveName, BackupDir, BackupGroup, BackupNamespace, BackupPart,
> -    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, PathPattern,
> -    PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
> +    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, InstanceId,
> +    PathPattern, PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
>      BACKUP_ID_SCHEMA, BACKUP_NAMESPACE_SCHEMA, BACKUP_TIME_SCHEMA, BACKUP_TYPE_SCHEMA,
>      CATALOG_NAME, ENCRYPTED_KEY_BLOB_NAME, MANIFEST_BLOB_NAME,
>  };
> @@ -139,6 +139,39 @@ fn record_repository(repo: &BackupRepository) {
>      );
>  }
>
> +#[api(
> +    input: {
> +        properties: {
> +            repository: {
> +                schema: REPO_URL_SCHEMA,
> +                optional: true,
> +            },
> +            "output-format": {
> +                schema: OUTPUT_FORMAT,
> +                optional: true,
> +            },
> +        },
> +    },
> +)]
> +/// Start garbage collection for a specific repository.

nit: that description probably should read "Get the instance ID of a PBS
host." instead ^^

> +async fn get_instance_id(param: Value) -> Result<Value, Error> {
> +    let repo = extract_repository_from_value(&param)?;
> +    let output_format = get_output_format(&param);
> +    let client = connect(&repo)?;
> +
> +    let path = format!("api2/json/nodes/localhost/instance-id");
> +    let mut result = client.get(&path, None).await?;
> +
> +    let id: InstanceId = serde_json::from_value(result["data"].take())?;
> +
> +    if output_format == "text" {
> +        println!("instance-id: {}", id.instance_id);
> +    } else {
> +        format_and_print_result(&id, &output_format);
> +    }
> +    Ok(Value::Null)
> +}
> +
>  async fn api_datastore_list_snapshots(
>      client: &HttpClient,
>      store: &str,
> @@ -2076,6 +2109,9 @@ fn main() {
>      let version_cmd_def =
>          CliCommand::new(&API_METHOD_API_VERSION).completion_cb("repository", complete_repository);
>
> +    let instance_id_cmd_def = CliCommand::new(&API_METHOD_GET_INSTANCE_ID)
> +        .completion_cb("repository", complete_repository);
> +
>      let change_owner_cmd_def = CliCommand::new(&API_METHOD_CHANGE_BACKUP_OWNER)
>          .arg_param(&["group", "new-owner"])
>          .completion_cb("ns", complete_namespace)
> @@ -2086,6 +2122,7 @@ fn main() {
>      let cmd_def = CliCommandMap::new()
>          .insert("backup", backup_cmd_def)
>          .insert("garbage-collect", garbage_collect_cmd_def)
> +        .insert("instance-id", instance_id_cmd_def)
>          .insert("list", list_cmd_def)
>          .insert("login", login_cmd_def)
>          .insert("logout", logout_cmd_def)





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route
  2026-04-13 13:26   ` Shannon Sterz
@ 2026-04-13 13:37     ` Lukas Wagner
  0 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 13:37 UTC (permalink / raw)
  To: Shannon Sterz, Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 3:26 PM CEST, Shannon Sterz wrote:
> On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
>> This API allows us to retrieve the instance ID of PBS storages. This is
>> useful to establish a mapping between PBS storage and PBS remotes in
>> PDM.
>>
>> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
>> ---
>>
>> Notes:
>>     Maybe we want to make this more general and just call it /id or
>>     something, in case we want to use a similar mechanism for other storage
>>     types as well?
>>
>>     Also could make sense to cache the response.
>>
>>  src/PVE/API2/Storage/Status.pm | 50 +++++++++++++++++++++++++++++++++-
>>  1 file changed, 49 insertions(+), 1 deletion(-)
>>
>> diff --git a/src/PVE/API2/Storage/Status.pm b/src/PVE/API2/Storage/Status.pm
>> index 8225c3a..52aa673 100644
>> --- a/src/PVE/API2/Storage/Status.pm
>> +++ b/src/PVE/API2/Storage/Status.pm
>> @@ -14,7 +14,7 @@ use PVE::JSONSchema qw(get_standard_option);
>>  use PVE::RESTHandler;
>>  use PVE::RPCEnvironment;
>>  use PVE::RRD;
>> -use PVE::Tools qw(run_command);
>> +use PVE::Tools qw(run_command extract_param);
>>
>>  use PVE::API2::Storage::Content;
>>  use PVE::API2::Storage::FileRestore;
>> @@ -308,6 +308,7 @@ __PACKAGE__->register_method({
>>              { subdir => 'download-url' },
>>              { subdir => 'file-restore' },
>>              { subdir => 'import-metadata' },
>> +            { subdir => 'instance-id' },
>>              { subdir => 'oci-registry-pull' },
>>              { subdir => 'prunebackups' },
>>              { subdir => 'rrd' },
>> @@ -1118,4 +1119,51 @@ __PACKAGE__->register_method({
>>      },
>>  });
>>
>> +__PACKAGE__->register_method({
>> +    name => 'instance_id',
>> +    path => '{storage}/instance-id',
>> +    method => 'GET',
>> +    description => "Return unique storage instance ID (PBS only)",
>> +    permissions => {
>> +        check => ['perm', '/storage/{storage}', ['Datastore.Audit']],
>> +    },
>> +    protected => 1,
>> +    proxyto => 'node',
>> +    parameters => {
>> +        additionalProperties => 0,
>> +        properties => {
>> +            node => get_standard_option('pve-node'),
>> +            storage => get_standard_option('pve-storage-id'),
>> +        },
>> +    },
>> +    returns => {
>> +        type => "object",
>> +        properties => {
>> +            'instance-id' => {
>> +                type => 'string',
>> +                description => 'Unique instance ID',
>> +            },
>> +        },
>> +    },
>> +    code => sub {
>> +        my ($param) = @_;
>> +
>> +        my $rpcenv = PVE::RPCEnvironment::get();
>> +        my $user = $rpcenv->get_user();
>
> sorry if im missing something, but are these two lines a copy-paste
> mistake or do you rely on a side-effect of `get_user()` here (i.e.
> making sure that this function is called in an `RPCEnvironment` with a
> set user)?
>

argh yeah, sorry - I copied the handler from somewhere else and forgot
to clean this part out!

Thanks! :)


>> +        my $storeid = extract_param($param, 'storage');
>> +
>> +        my $cfg = PVE::Storage::config();
>> +        my $scfg = PVE::Storage::storage_config($cfg, $storeid);
>> +
>> +        raise_param_exc({ 'storage' => "Only PBS storages supported." })
>> +            if $scfg->{type} ne 'pbs';
>> +
>> +        my $client = PVE::PBSClient->new($scfg, $storeid);
>> +        my $ret = $client->get_instance_id();
>> +
>> +        return $ret;
>> +    },
>> +});
>> +
>>  1;





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH proxmox-backup 5/7] manager: add instance-id subcommand
  2026-04-13 13:26   ` Shannon Sterz
@ 2026-04-13 13:38     ` Lukas Wagner
  0 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 13:38 UTC (permalink / raw)
  To: Shannon Sterz, Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 3:26 PM CEST, Shannon Sterz wrote:
> On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
>> For the sake of completeness also allow to query the instance ID from
>> the proxmox-backup-manager admin tool.
>>
>> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
>> ---
>>  src/bin/proxmox_backup_manager/node.rs | 27 ++++++++++++++++++++++++++
>>  1 file changed, 27 insertions(+)
>>
>> diff --git a/src/bin/proxmox_backup_manager/node.rs b/src/bin/proxmox_backup_manager/node.rs
>> index 4da61690f..34c481587 100644
>> --- a/src/bin/proxmox_backup_manager/node.rs
>> +++ b/src/bin/proxmox_backup_manager/node.rs
>> @@ -32,9 +32,36 @@ fn get_node_config(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Valu
>>      Ok(Value::Null)
>>  }
>>
>> +#[api(
>> +    input: {
>> +        properties: {
>> +            "output-format": {
>> +                schema: OUTPUT_FORMAT,
>> +                optional: true,
>> +            },
>> +        }
>> +    }
>> +)]
>> +/// Show node configuration
>
> nit: this description should probably also be something like "Get the
> instance ID of the current PBS instance." or similar.
>

Ack! sorry for the copy-paste mistake, I somewhat rushed this so that we
can potentially get this in for the PBS release

>> +fn get_instance_id(param: Value, rpcenv: &mut dyn RpcEnvironment) -> Result<Value, Error> {
>> +    let output_format = get_output_format(&param);
>> +
>> +    let info = &api2::node::API_METHOD_GET_INSTANCE_ID;
>> +    let mut data = match info.handler {
>> +        ApiHandler::Sync(handler) => (handler)(param, info, rpcenv)?,
>> +        _ => unreachable!(),
>> +    };
>> +
>> +    let options = default_table_format_options();
>> +    format_and_print_result_full(&mut data, &info.returns, &output_format, &options);
>> +
>> +    Ok(Value::Null)
>> +}
>> +
>>  pub fn node_commands() -> CommandLineInterface {
>>      let cmd_def = CliCommandMap::new()
>>          .insert("show", CliCommand::new(&API_METHOD_GET_NODE_CONFIG))
>> +        .insert("instance-id", CliCommand::new(&API_METHOD_GET_INSTANCE_ID))
>>          .insert(
>>              "update",
>>              CliCommand::new(&api2::node::config::API_METHOD_UPDATE_NODE_CONFIG)





^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command
  2026-04-13 13:26   ` Shannon Sterz
@ 2026-04-13 13:39     ` Lukas Wagner
  0 siblings, 0 replies; 14+ messages in thread
From: Lukas Wagner @ 2026-04-13 13:39 UTC (permalink / raw)
  To: Shannon Sterz, Lukas Wagner, pbs-devel, pve-devel

On Mon Apr 13, 2026 at 3:26 PM CEST, Shannon Sterz wrote:
> On Mon Apr 13, 2026 at 2:10 PM CEST, Lukas Wagner wrote:
>> This allows users to query the instance-id from the
>> proxmox-backup-client tool. This will also be used by the PBS client in
>> PVE to lookup the instance-id from a yet to be introduced API endpoint
>> that returns the instance-id for a given PBS storage.
>>
>> Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
>> ---
>>  proxmox-backup-client/src/main.rs | 41 +++++++++++++++++++++++++++++--
>>  1 file changed, 39 insertions(+), 2 deletions(-)
>>
>> diff --git a/proxmox-backup-client/src/main.rs b/proxmox-backup-client/src/main.rs
>> index 2ada87bdd..9f4a82e26 100644
>> --- a/proxmox-backup-client/src/main.rs
>> +++ b/proxmox-backup-client/src/main.rs
>> @@ -25,8 +25,8 @@ use pxar::accessor::{MaybeReady, ReadAt, ReadAtOperation};
>>
>>  use pbs_api_types::{
>>      ArchiveType, Authid, BackupArchiveName, BackupDir, BackupGroup, BackupNamespace, BackupPart,
>> -    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, PathPattern,
>> -    PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
>> +    BackupType, ClientRateLimitConfig, CryptMode, Fingerprint, GroupListItem, InstanceId,
>> +    PathPattern, PruneJobOptions, PruneListItem, RateLimitConfig, SnapshotListItem, StorageStatus,
>>      BACKUP_ID_SCHEMA, BACKUP_NAMESPACE_SCHEMA, BACKUP_TIME_SCHEMA, BACKUP_TYPE_SCHEMA,
>>      CATALOG_NAME, ENCRYPTED_KEY_BLOB_NAME, MANIFEST_BLOB_NAME,
>>  };
>> @@ -139,6 +139,39 @@ fn record_repository(repo: &BackupRepository) {
>>      );
>>  }
>>
>> +#[api(
>> +    input: {
>> +        properties: {
>> +            repository: {
>> +                schema: REPO_URL_SCHEMA,
>> +                optional: true,
>> +            },
>> +            "output-format": {
>> +                schema: OUTPUT_FORMAT,
>> +                optional: true,
>> +            },
>> +        },
>> +    },
>> +)]
>> +/// Start garbage collection for a specific repository.
>
> nit: that description probably should read "Get the instance ID of a PBS
> host." instead ^^
>

absolutely, this was a copy-paste oversight, thanks!

>> +async fn get_instance_id(param: Value) -> Result<Value, Error> {
>> +    let repo = extract_repository_from_value(&param)?;
>> +    let output_format = get_output_format(&param);
>> +    let client = connect(&repo)?;
>> +
>> +    let path = format!("api2/json/nodes/localhost/instance-id");
>> +    let mut result = client.get(&path, None).await?;
>> +
>> +    let id: InstanceId = serde_json::from_value(result["data"].take())?;
>> +
>> +    if output_format == "text" {
>> +        println!("instance-id: {}", id.instance_id);
>> +    } else {
>> +        format_and_print_result(&id, &output_format);
>> +    }
>> +    Ok(Value::Null)
>> +}
>> +
>>  async fn api_datastore_list_snapshots(
>>      client: &HttpClient,
>>      store: &str,
>> @@ -2076,6 +2109,9 @@ fn main() {
>>      let version_cmd_def =
>>          CliCommand::new(&API_METHOD_API_VERSION).completion_cb("repository", complete_repository);
>>
>> +    let instance_id_cmd_def = CliCommand::new(&API_METHOD_GET_INSTANCE_ID)
>> +        .completion_cb("repository", complete_repository);
>> +
>>      let change_owner_cmd_def = CliCommand::new(&API_METHOD_CHANGE_BACKUP_OWNER)
>>          .arg_param(&["group", "new-owner"])
>>          .completion_cb("ns", complete_namespace)
>> @@ -2086,6 +2122,7 @@ fn main() {
>>      let cmd_def = CliCommandMap::new()
>>          .insert("backup", backup_cmd_def)
>>          .insert("garbage-collect", garbage_collect_cmd_def)
>> +        .insert("instance-id", instance_id_cmd_def)
>>          .insert("list", list_cmd_def)
>>          .insert("login", login_cmd_def)
>>          .insert("logout", logout_cmd_def)





^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2026-04-13 13:39 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-04-13 12:10 [RFC common/proxmox{,-backup}/storage 0/7] establish unique instance-id for PBS nodes Lukas Wagner
2026-04-13 12:10 ` [PATCH proxmox 1/7] pbs-api-types: add InstanceId response type Lukas Wagner
2026-04-13 12:10 ` [PATCH proxmox 2/7] systemd: add support for machine-id generation Lukas Wagner
2026-04-13 12:10 ` [PATCH proxmox-backup 3/7] api: add /nodes/localhost/instance-id Lukas Wagner
2026-04-13 12:10 ` [PATCH proxmox-backup 4/7] client: add 'instance-id' sub-command Lukas Wagner
2026-04-13 13:26   ` Shannon Sterz
2026-04-13 13:39     ` Lukas Wagner
2026-04-13 12:10 ` [PATCH proxmox-backup 5/7] manager: add instance-id subcommand Lukas Wagner
2026-04-13 13:26   ` Shannon Sterz
2026-04-13 13:38     ` Lukas Wagner
2026-04-13 12:10 ` [PATCH common 6/7] pbs-client: add support for the 'instance id' command Lukas Wagner
2026-04-13 12:10 ` [PATCH pve-storage 7/7] api: add /nodes/<node>/storage/<storage>/instance-id route Lukas Wagner
2026-04-13 13:26   ` Shannon Sterz
2026-04-13 13:37     ` Lukas Wagner

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Service provided by Proxmox Server Solutions GmbH | Privacy | Legal