summaryrefslogtreecommitdiff
path: root/src/PVE/API2/Network/SDN/Ipams.pm
diff options
context:
space:
mode:
authorStefan Hanreich <s.hanreich@proxmox.com>2023-11-20 17:28:32 +0100
committerThomas Lamprecht <t.lamprecht@proxmox.com>2023-11-20 17:40:36 +0100
commit359416aa52e6ed137a8662a9d3f6fa4a50a5e7ec (patch)
tree22d40e668c1df48fde91d0074348d64bb0112f24 /src/PVE/API2/Network/SDN/Ipams.pm
parent39062bc53a95ef5a0e45171e61aa5df3e52ca898 (diff)
api: refactor URL structure for Ipam
The initial URL structure was less than optimal due to Ipam as well as Ipams being endpoints in the API, which are too similar and might be confusing to users. Move the listing of PVE IPAM to /ipams/pve/status Move the create / update / delete endpoints to /vnets/{vnetid}/ips Signed-off-by: Stefan Hanreich <s.hanreich@proxmox.com>
Diffstat (limited to 'src/PVE/API2/Network/SDN/Ipams.pm')
-rw-r--r--src/PVE/API2/Network/SDN/Ipams.pm83
1 files changed, 83 insertions, 0 deletions
diff --git a/src/PVE/API2/Network/SDN/Ipams.pm b/src/PVE/API2/Network/SDN/Ipams.pm
index 6410e8e..d6e0bc8 100644
--- a/src/PVE/API2/Network/SDN/Ipams.pm
+++ b/src/PVE/API2/Network/SDN/Ipams.pm
@@ -12,6 +12,9 @@ use PVE::Network::SDN::Ipams::Plugin;
use PVE::Network::SDN::Ipams::PVEPlugin;
use PVE::Network::SDN::Ipams::PhpIpamPlugin;
use PVE::Network::SDN::Ipams::NetboxPlugin;
+use PVE::Network::SDN::Dhcp;
+use PVE::Network::SDN::Vnets;
+use PVE::Network::SDN::Zones;
use Storable qw(dclone);
use PVE::JSONSchema qw(get_standard_option);
@@ -245,4 +248,84 @@ __PACKAGE__->register_method ({
return undef;
}});
+__PACKAGE__->register_method ({
+ name => 'ipamindex',
+ path => '{ipam}/status',
+ method => 'GET',
+ description => 'List PVE IPAM Entries',
+ protected => 1,
+ permissions => {
+ description => "Only list entries where you have 'SDN.Audit' or 'SDN.Allocate' permissions on '/sdn/zones/<zone>/<vnet>'",
+ user => 'all',
+ },
+ parameters => {
+ additionalProperties => 0,
+ properties => {
+ ipam => get_standard_option('pve-sdn-ipam-id', {
+ completion => \&PVE::Network::SDN::Ipams::complete_sdn_ipams,
+ }),
+ },
+ },
+ returns => {
+ type => 'array',
+ },
+ code => sub {
+ my ($param) = @_;
+
+ my $id = extract_param($param, 'ipam');
+ die "Currently only PVE IPAM is supported!" if $id ne 'pve';
+
+ my $rpcenv = PVE::RPCEnvironment::get();
+ my $authuser = $rpcenv->get_user();
+ my $privs = [ 'SDN.Audit', 'SDN.Allocate' ];
+
+ my $ipam_plugin = PVE::Network::SDN::Ipams::Plugin->lookup('pve');
+ my $ipam_db = $ipam_plugin->read_db();
+
+ my $result = [];
+
+ for my $zone_id (keys %{$ipam_db->{zones}}) {
+ my $zone_config = PVE::Network::SDN::Zones::get_zone($zone_id, 1);
+ next if !$zone_config || $zone_config->{ipam} ne 'pve' || !$zone_config->{dhcp};
+
+ my $zone = $ipam_db->{zones}->{$zone_id};
+
+ my $vnets = PVE::Network::SDN::Zones::get_vnets($zone_id, 1);
+
+ for my $subnet_cidr (keys %{$zone->{subnets}}) {
+ my $subnet = $zone->{subnets}->{$subnet_cidr};
+ my $ip = new NetAddr::IP($subnet_cidr) or die 'Found invalid CIDR in IPAM';
+
+ my $vnet = undef;
+ for my $vnet_id (keys %$vnets) {
+ eval {
+ my ($zone, $subnetid, $subnet_cfg, $ip) = PVE::Network::SDN::Vnets::get_subnet_from_vnet_ip(
+ $vnet_id,
+ $ip->addr,
+ );
+
+ $vnet = $subnet_cfg->{vnet};
+ };
+
+ last if $vnet;
+ }
+
+ next if !$vnet || !$rpcenv->check_any($authuser, "/sdn/zones/$zone_id/$vnet", $privs, 1);
+
+ for my $ip (keys %{$subnet->{ips}}) {
+ my $entry = $subnet->{ips}->{$ip};
+ $entry->{zone} = $zone_id;
+ $entry->{subnet} = $subnet_cidr;
+ $entry->{ip} = $ip;
+ $entry->{vnet} = $vnet;
+
+ push @$result, $entry;
+ }
+ }
+ }
+
+ return $result;
+ },
+});
+
1;