From 44ef7ec0590116e8478125dc564f202baaf3f517 Mon Sep 17 00:00:00 2001 From: Wei Zhou Date: Mon, 30 Jan 2023 13:06:38 +0100 Subject: [PATCH 1/5] server: fix cannot get systemvm ips in dedicated ranges (Issue 6698) --- .../java/com/cloud/api/ApiResponseHelper.java | 2 +- .../ConfigurationManagerImpl.java | 1 - .../cloud/network/IpAddressManagerImpl.java | 114 +++++++++--------- ui/public/locales/en.json | 1 + .../views/infra/network/IpRangesTabPublic.vue | 6 +- 5 files changed, 65 insertions(+), 59 deletions(-) diff --git a/server/src/main/java/com/cloud/api/ApiResponseHelper.java b/server/src/main/java/com/cloud/api/ApiResponseHelper.java index 437ff05d28d0..6c9229bc6ec2 100644 --- a/server/src/main/java/com/cloud/api/ApiResponseHelper.java +++ b/server/src/main/java/com/cloud/api/ApiResponseHelper.java @@ -855,7 +855,7 @@ public VlanIpRangeResponse createVlanIpRangeResponse(Class params) { AssignIpAddressSearch.and("dc", AssignIpAddressSearch.entity().getDataCenterId(), Op.EQ); AssignIpAddressSearch.and("allocated", AssignIpAddressSearch.entity().getAllocatedTime(), Op.NULL); AssignIpAddressSearch.and("vlanId", AssignIpAddressSearch.entity().getVlanId(), Op.IN); - if (SystemVmPublicIpReservationModeStrictness.value()) { - AssignIpAddressSearch.and("forSystemVms", AssignIpAddressSearch.entity().isForSystemVms(), Op.EQ); - } + AssignIpAddressSearch.and("forSystemVms", AssignIpAddressSearch.entity().isForSystemVms(), Op.EQ); + SearchBuilder vlanSearch = _vlanDao.createSearchBuilder(); vlanSearch.and("type", vlanSearch.entity().getVlanType(), Op.EQ); vlanSearch.and("networkId", vlanSearch.entity().getNetworkId(), Op.EQ); @@ -840,49 +839,6 @@ public List doInTransaction(TransactionStatus status) throws Insuff errorMessage.append(" zone id=" + dcId); } - // If owner has dedicated Public IP ranges, fetch IP from the dedicated range - // Otherwise fetch IP from the system pool - Network network = _networksDao.findById(guestNetworkId); - //Checking if network is null in the case of system VM's. At the time of allocation of IP address to systemVm, no network is present. - if(network == null || !(network.getGuestType() == GuestType.Shared && zone.getNetworkType() == NetworkType.Advanced)) { - List maps = _accountVlanMapDao.listAccountVlanMapsByAccount(owner.getId()); - for (AccountVlanMapVO map : maps) { - if (vlanDbIds == null || vlanDbIds.contains(map.getVlanDbId())) - dedicatedVlanDbIds.add(map.getVlanDbId()); - } - } - List domainMaps = _domainVlanMapDao.listDomainVlanMapsByDomain(owner.getDomainId()); - for (DomainVlanMapVO map : domainMaps) { - if (vlanDbIds == null || vlanDbIds.contains(map.getVlanDbId())) - dedicatedVlanDbIds.add(map.getVlanDbId()); - } - List nonDedicatedVlans = _vlanDao.listZoneWideNonDedicatedVlans(dcId); - for (VlanVO nonDedicatedVlan : nonDedicatedVlans) { - if (vlanDbIds == null || vlanDbIds.contains(nonDedicatedVlan.getId())) - nonDedicatedVlanDbIds.add(nonDedicatedVlan.getId()); - } - - if (vlanUse == VlanType.VirtualNetwork) { - if (!dedicatedVlanDbIds.isEmpty()) { - fetchFromDedicatedRange = true; - sc.setParameters("vlanId", dedicatedVlanDbIds.toArray()); - errorMessage.append(", vlanId id=" + Arrays.toString(dedicatedVlanDbIds.toArray())); - } else if (!nonDedicatedVlanDbIds.isEmpty()) { - sc.setParameters("vlanId", nonDedicatedVlanDbIds.toArray()); - errorMessage.append(", vlanId id=" + Arrays.toString(nonDedicatedVlanDbIds.toArray())); - } else { - if (podId != null) { - InsufficientAddressCapacityException ex = new InsufficientAddressCapacityException("Insufficient address capacity", Pod.class, podId); - ex.addProxyObject(ApiDBUtils.findPodById(podId).getUuid()); - throw ex; - } - s_logger.warn(errorMessage.toString()); - InsufficientAddressCapacityException ex = new InsufficientAddressCapacityException("Insufficient address capacity", DataCenter.class, dcId); - ex.addProxyObject(ApiDBUtils.findZoneById(dcId).getUuid()); - throw ex; - } - } - sc.setParameters("dc", dcId); // for direct network take ip addresses only from the vlans belonging to the network @@ -895,6 +851,8 @@ public List doInTransaction(TransactionStatus status) throws Insuff errorMessage.append(", requested gateway=" + requestedGateway); } sc.setJoinParameters("vlan", "type", vlanUse); + + Network network = _networksDao.findById(guestNetworkId); String routerIpAddress = null; if (network != null) { NetworkDetailVO routerIpDetail = _networkDetailsDao.findDetail(network.getId(), ApiConstants.ROUTER_IP); @@ -909,18 +867,66 @@ public List doInTransaction(TransactionStatus status) throws Insuff boolean ascOrder = ! forSystemVms; Filter filter = new Filter(IPAddressVO.class, "forSystemVms", ascOrder, 0l, 1l); - if (SystemVmPublicIpReservationModeStrictness.value()) { - sc.setParameters("forSystemVms", forSystemVms); - } filter.addOrderBy(IPAddressVO.class,"vlanId", true); - List addrs; + List addrs = new ArrayList<>(); - if (lockOneRow) { - addrs = _ipAddressDao.lockRows(sc, filter, true); - } else { - addrs = new ArrayList<>(_ipAddressDao.search(sc, null)); + if (forSystemVms) { + // Get Public IPs for system vms in dedicated ranges + sc.setParameters("forSystemVms", true); + if (lockOneRow) { + addrs = _ipAddressDao.lockRows(sc, filter, true); + } else { + addrs = new ArrayList<>(_ipAddressDao.search(sc, null)); + } + } + if (vlanUse == VlanType.VirtualNetwork && (!lockOneRow || (lockOneRow && addrs.size() == 0)) && + !(forSystemVms && SystemVmPublicIpReservationModeStrictness.value())) { + sc.setParameters("forSystemVms", false); + // If owner has dedicated Public IP ranges, fetch IP from the dedicated range + // Otherwise fetch IP from the system pool + // Checking if network is null in the case of system VM's. At the time of allocation of IP address to systemVm, no network is present. + if (network == null || !(network.getGuestType() == GuestType.Shared && zone.getNetworkType() == NetworkType.Advanced)) { + List maps = _accountVlanMapDao.listAccountVlanMapsByAccount(owner.getId()); + for (AccountVlanMapVO map : maps) { + if (vlanDbIds == null || vlanDbIds.contains(map.getVlanDbId())) + dedicatedVlanDbIds.add(map.getVlanDbId()); + } + } + List domainMaps = _domainVlanMapDao.listDomainVlanMapsByDomain(owner.getDomainId()); + for (DomainVlanMapVO map : domainMaps) { + if (vlanDbIds == null || vlanDbIds.contains(map.getVlanDbId())) + dedicatedVlanDbIds.add(map.getVlanDbId()); + } + List nonDedicatedVlans = _vlanDao.listZoneWideNonDedicatedVlans(dcId); + for (VlanVO nonDedicatedVlan : nonDedicatedVlans) { + if (vlanDbIds == null || vlanDbIds.contains(nonDedicatedVlan.getId())) + nonDedicatedVlanDbIds.add(nonDedicatedVlan.getId()); + } + if (!dedicatedVlanDbIds.isEmpty()) { + fetchFromDedicatedRange = true; + sc.setParameters("vlanId", dedicatedVlanDbIds.toArray()); + errorMessage.append(", vlanId id=" + Arrays.toString(dedicatedVlanDbIds.toArray())); + } else if (!nonDedicatedVlanDbIds.isEmpty()) { + sc.setParameters("vlanId", nonDedicatedVlanDbIds.toArray()); + errorMessage.append(", vlanId id=" + Arrays.toString(nonDedicatedVlanDbIds.toArray())); + } else { + if (podId != null) { + InsufficientAddressCapacityException ex = new InsufficientAddressCapacityException("Insufficient address capacity", Pod.class, podId); + ex.addProxyObject(ApiDBUtils.findPodById(podId).getUuid()); + throw ex; + } + s_logger.warn(errorMessage.toString()); + InsufficientAddressCapacityException ex = new InsufficientAddressCapacityException("Insufficient address capacity", DataCenter.class, dcId); + ex.addProxyObject(ApiDBUtils.findZoneById(dcId).getUuid()); + throw ex; + } + if (lockOneRow) { + addrs = _ipAddressDao.lockRows(sc, filter, true); + } else { + addrs = new ArrayList<>(_ipAddressDao.search(sc, null)); + } } // If all the dedicated IPs of the owner are in use fetch an IP from the system pool diff --git a/ui/public/locales/en.json b/ui/public/locales/en.json index a4d0d0b6197c..6883ae9789c5 100644 --- a/ui/public/locales/en.json +++ b/ui/public/locales/en.json @@ -1739,6 +1739,7 @@ "label.suspend.project": "Suspend project", "label.switch.type": "Switch type", "label.sync.storage": "Sync storage pool", +"label.system.ip.pool": "System Pool", "label.system.offering": "System offering", "label.system.offerings": "System offerings", "label.system.service.offering": "System service offering", diff --git a/ui/src/views/infra/network/IpRangesTabPublic.vue b/ui/src/views/infra/network/IpRangesTabPublic.vue index 247a8faf0d41..d7f743fda138 100644 --- a/ui/src/views/infra/network/IpRangesTabPublic.vue +++ b/ui/src/views/infra/network/IpRangesTabPublic.vue @@ -47,21 +47,21 @@ {{ record.endip || record.endipv6 }}