From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from firstgate.proxmox.com (firstgate.proxmox.com [IPv6:2a01:7e0:0:424::9]) by lore.proxmox.com (Postfix) with ESMTPS id 2CF1D1FF16B for ; Fri, 7 Nov 2025 09:58:57 +0100 (CET) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id 195CDB87E; Fri, 7 Nov 2025 09:59:39 +0100 (CET) From: Stefan Hanreich To: pdm-devel@lists.proxmox.com Date: Fri, 7 Nov 2025 09:59:24 +0100 Message-ID: <20251107085934.118815-5-s.hanreich@proxmox.com> X-Mailer: git-send-email 2.47.3 In-Reply-To: <20251107085934.118815-1-s.hanreich@proxmox.com> References: <20251107085934.118815-1-s.hanreich@proxmox.com> MIME-Version: 1.0 X-SPAM-LEVEL: Spam detection results: 0 AWL -0.181 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 KAM_LAZY_DOMAIN_SECURITY 1 Sending domain does not have any anti-forgery methods RDNS_NONE 0.793 Delivered to internal network by a host with no rDNS SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_NONE 0.001 SPF: sender does not publish an SPF Record Subject: [pdm-devel] [PATCH proxmox-datacenter-manager 1/5] server: api: sdn: add ip-vrf endpoint X-BeenThere: pdm-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox Datacenter Manager development discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: Proxmox Datacenter Manager development discussion Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: pdm-devel-bounces@lists.proxmox.com Sender: "pdm-devel" Calls the respective Proxmox VE endpoint to obtain status information about the IP-VRF of an EVPN zone. Since the status is per-node, use the existing nodes subdirectory instead of the general SDN subdirectory, mirroring the API paths used in Proxmox VE. In order to avoid having too many SDN-specific modules for a single API call, introduce a submodule in the sdn module directly. If needed, this can be easily factored out in the future. Signed-off-by: Stefan Hanreich --- lib/pdm-client/src/lib.rs | 12 ++++++++ server/src/api/nodes/mod.rs | 2 ++ server/src/api/nodes/sdn.rs | 58 +++++++++++++++++++++++++++++++++++++ server/src/api/pve/node.rs | 3 +- 4 files changed, 74 insertions(+), 1 deletion(-) create mode 100644 server/src/api/nodes/sdn.rs diff --git a/lib/pdm-client/src/lib.rs b/lib/pdm-client/src/lib.rs index 0cab769..e22d139 100644 --- a/lib/pdm-client/src/lib.rs +++ b/lib/pdm-client/src/lib.rs @@ -66,6 +66,8 @@ pub mod types { pub use pve_api_types::{ListControllersType, ListZonesType, SdnObjectState}; pub use pve_api_types::StorageStatus as PveStorageStatus; + + pub use pve_api_types::SdnZoneIpVrf; } pub struct PdmClient(pub T); @@ -1051,6 +1053,16 @@ impl PdmClient { Ok(self.0.post(path, ¶ms).await?.expect_json()?.data) } + pub async fn pve_sdn_zone_get_ip_vrf( + &self, + remote: &str, + node: &str, + zone: &str, + ) -> Result, Error> { + let path = format!("/api2/extjs/pve/remotes/{remote}/nodes/{node}/sdn/zones/{zone}/ip-vrf"); + Ok(self.0.get(&path).await?.expect_json()?.data) + } + /// uses /pbs/probe-tls to probe the tls connection to the given host pub async fn pbs_probe_tls( &self, diff --git a/server/src/api/nodes/mod.rs b/server/src/api/nodes/mod.rs index 6f30ba7..66f88f3 100644 --- a/server/src/api/nodes/mod.rs +++ b/server/src/api/nodes/mod.rs @@ -10,6 +10,7 @@ pub mod dns; pub mod journal; pub mod network; pub mod rrddata; +pub mod sdn; pub mod syslog; pub mod tasks; pub mod termproxy; @@ -45,6 +46,7 @@ pub const SUBDIRS: SubdirMap = &sorted!([ ("journal", &journal::ROUTER), ("network", &network::ROUTER), ("rrdata", &rrddata::ROUTER), + ("sdn", &sdn::ROUTER), ("syslog", &syslog::ROUTER), ("tasks", &tasks::ROUTER), ("termproxy", &termproxy::ROUTER), diff --git a/server/src/api/nodes/sdn.rs b/server/src/api/nodes/sdn.rs new file mode 100644 index 0000000..9ca6130 --- /dev/null +++ b/server/src/api/nodes/sdn.rs @@ -0,0 +1,58 @@ +use anyhow::{anyhow, Error}; +use http::StatusCode; + +use pdm_api_types::{remotes::REMOTE_ID_SCHEMA, sdn::SDN_ID_SCHEMA, NODE_SCHEMA}; +use proxmox_router::{list_subdirs_api_method, Router, SubdirMap}; +use proxmox_schema::api; +use pve_api_types::SdnZoneIpVrf; + +use crate::api::pve::{connect, get_remote}; + +mod zones { + use super::*; + + const ZONE_SUBDIRS: SubdirMap = &[("ip-vrf", &Router::new().get(&API_METHOD_GET_IP_VRF))]; + + const ZONE_ROUTER: Router = Router::new() + .get(&list_subdirs_api_method!(ZONE_SUBDIRS)) + .subdirs(ZONE_SUBDIRS); + + pub const ROUTER: Router = Router::new().match_all("zone", &ZONE_ROUTER); + + #[api( + input: { + properties: { + remote: { schema: REMOTE_ID_SCHEMA }, + node: { schema: NODE_SCHEMA }, + zone: { schema: SDN_ID_SCHEMA }, + }, + }, + returns: { type: SdnZoneIpVrf }, + )] + /// Get the IP-VRF for an EVPN zone for a node on a given remote + async fn get_ip_vrf( + remote: String, + node: String, + zone: String, + ) -> Result, Error> { + let (remote_config, _) = pdm_config::remotes::config()?; + let remote = get_remote(&remote_config, &remote)?; + let client = connect(remote)?; + + client + .get_zone_ip_vrf(&node, &zone) + .await + .map_err(|err| match err { + proxmox_client::Error::Api(StatusCode::NOT_IMPLEMENTED, _msg) => { + anyhow!("remote {} does not support the zone ip-vrf API call, please upgrade to the newest version!", remote.id) + } + _ => err.into() + }) + } +} + +const SUBDIRS: SubdirMap = &[("zone", &zones::ROUTER)]; + +pub const ROUTER: Router = Router::new() + .get(&list_subdirs_api_method!(SUBDIRS)) + .subdirs(SUBDIRS); diff --git a/server/src/api/pve/node.rs b/server/src/api/pve/node.rs index 301c0b1..dae890e 100644 --- a/server/src/api/pve/node.rs +++ b/server/src/api/pve/node.rs @@ -7,7 +7,7 @@ use proxmox_sortable_macro::sortable; use pdm_api_types::{remotes::REMOTE_ID_SCHEMA, NODE_SCHEMA, PRIV_RESOURCE_AUDIT}; use pve_api_types::StorageContent; -use crate::api::pve::storage; +use crate::api::{nodes::sdn, pve::storage}; pub const ROUTER: Router = Router::new() .get(&list_subdirs_api_method!(SUBDIRS)) @@ -18,6 +18,7 @@ const SUBDIRS: SubdirMap = &sorted!([ ("apt", &crate::api::remote_updates::APT_ROUTER), ("rrddata", &super::rrddata::NODE_RRD_ROUTER), ("network", &Router::new().get(&API_METHOD_GET_NETWORK)), + ("sdn", &sdn::ROUTER), ("storage", &STORAGE_ROUTER), ("status", &Router::new().get(&API_METHOD_GET_STATUS)), ]); -- 2.47.3 _______________________________________________ pdm-devel mailing list pdm-devel@lists.proxmox.com https://lists.proxmox.com/cgi-bin/mailman/listinfo/pdm-devel