This is an automated email from the ASF dual-hosted git repository.

winterhazel pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/cloudstack.git


The following commit(s) were added to refs/heads/main by this push:
     new 6f4445c5c1b Add offering preset variables for `Network` and `VPC` 
Quota tariffs (#11810)
6f4445c5c1b is described below

commit 6f4445c5c1b510a47b12dec1b61dc41dde02979b
Author: Henrique Sato <[email protected]>
AuthorDate: Mon Apr 27 09:36:37 2026 -0300

    Add offering preset variables for `Network` and `VPC` Quota tariffs (#11810)
    
    * Add offering preset variable to Network and VPC tariffs
    
    * Apply suggestions from code review
    
    Co-authored-by: Copilot <[email protected]>
    Co-authored-by: Fabricio Duarte <[email protected]>
    
    * Add tests
    
    ---------
    
    Co-authored-by: Copilot <[email protected]>
    Co-authored-by: Fabricio Duarte <[email protected]>
---
 ...n-daos-between-management-and-usage-context.xml |   2 +
 .../spring-engine-schema-core-daos-context.xml     |   2 -
 .../presetvariables/PresetVariableHelper.java      |  32 +++++-
 .../activationrule/presetvariables/Value.java      |  22 ++++
 .../presetvariables/PresetVariableHelperTest.java  | 127 +++++++++++++++++++++
 5 files changed, 182 insertions(+), 3 deletions(-)

diff --git 
a/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-common-daos-between-management-and-usage-context.xml
 
b/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-common-daos-between-management-and-usage-context.xml
index 1846c3c62a0..2c6869bd81e 100644
--- 
a/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-common-daos-between-management-and-usage-context.xml
+++ 
b/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-common-daos-between-management-and-usage-context.xml
@@ -73,5 +73,7 @@
        <bean id="volumeDaoImpl" class="com.cloud.storage.dao.VolumeDaoImpl" />
        <bean id="reservationDao" 
class="org.apache.cloudstack.reservation.dao.ReservationDaoImpl" />
     <bean id="backupOfferingDaoImpl" 
class="org.apache.cloudstack.backup.dao.BackupOfferingDaoImpl" />
+       <bean id="vpcOfferingDaoImpl" 
class="com.cloud.network.vpc.dao.VpcOfferingDaoImpl" />
+       <bean id="vpcOfferingDetailsDaoImpl" 
class="com.cloud.network.vpc.dao.VpcOfferingDetailsDaoImpl"/>
     <bean id="backupOfferingDetailsDaoImpl" 
class="org.apache.cloudstack.backup.dao.BackupOfferingDetailsDaoImpl" />
 </beans>
diff --git 
a/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
 
b/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
index edc14d9fa0c..ad3722577c2 100644
--- 
a/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
+++ 
b/engine/schema/src/main/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
@@ -236,13 +236,11 @@
   <bean id="volumeStatsDaoImpl" 
class="com.cloud.storage.dao.VolumeStatsDaoImpl" />
   <bean id="vpcDaoImpl" class="com.cloud.network.vpc.dao.VpcDaoImpl" />
   <bean id="vpcGatewayDaoImpl" 
class="com.cloud.network.vpc.dao.VpcGatewayDaoImpl" />
-  <bean id="vpcOfferingDaoImpl" 
class="com.cloud.network.vpc.dao.VpcOfferingDaoImpl" />
   <bean id="vpcOfferingJoinDaoImpl" 
class="com.cloud.api.query.dao.VpcOfferingJoinDaoImpl" />
   <bean id="vpcOfferingServiceMapDaoImpl" 
class="com.cloud.network.vpc.dao.VpcOfferingServiceMapDaoImpl" />
   <bean id="vpcServiceMapDaoImpl" 
class="com.cloud.network.vpc.dao.VpcServiceMapDaoImpl" />
   <bean id="vpnUserDaoImpl" class="com.cloud.network.dao.VpnUserDaoImpl" />
   <bean id="applicationLbRuleDaoImpl" 
class="org.apache.cloudstack.lb.dao.ApplicationLoadBalancerRuleDaoImpl" />
-  <bean id="vpcOfferingDetailsDaoImpl" 
class="com.cloud.network.vpc.dao.VpcOfferingDetailsDaoImpl"/>
   <bean id="networkDetailsDaoImpl" 
class="com.cloud.network.dao.NetworkDetailsDaoImpl" />
   <bean id="tungstenGuestNetworkIpAddressDaoImpl" 
class="com.cloud.network.dao.TungstenGuestNetworkIpAddressDaoImpl"/>
   <bean id="tungstenSecurityGroupRuleDaoImpl" 
class="com.cloud.network.security.dao.TungstenSecurityGroupRuleDaoImpl"/>
diff --git 
a/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelper.java
 
b/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelper.java
index a2fca7b80fd..cd87052e878 100644
--- 
a/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelper.java
+++ 
b/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelper.java
@@ -28,11 +28,12 @@ import java.util.stream.Collectors;
 import com.cloud.dc.ClusterDetailsDao;
 import com.cloud.dc.ClusterDetailsVO;
 import com.cloud.host.HostTagVO;
+import com.cloud.hypervisor.Hypervisor;
 import com.cloud.network.dao.NetworkVO;
+import com.cloud.network.vpc.VpcOfferingVO;
 import com.cloud.network.vpc.VpcVO;
 import javax.inject.Inject;
 
-import com.cloud.hypervisor.Hypervisor;
 import com.cloud.storage.StoragePoolTagVO;
 import org.apache.cloudstack.acl.RoleVO;
 import org.apache.cloudstack.acl.dao.RoleDao;
@@ -66,6 +67,7 @@ import com.cloud.domain.dao.DomainDao;
 import com.cloud.host.HostVO;
 import com.cloud.host.dao.HostDao;
 import com.cloud.host.dao.HostTagsDao;
+import com.cloud.network.vpc.dao.VpcOfferingDao;
 import com.cloud.offerings.NetworkOfferingVO;
 import com.cloud.offerings.dao.NetworkOfferingDao;
 import com.cloud.server.ResourceTag;
@@ -191,6 +193,9 @@ public class PresetVariableHelper {
     @Inject
     ClusterDetailsDao clusterDetailsDao;
 
+    @Inject
+    VpcOfferingDao vpcOfferingDao;
+
     protected boolean backupSnapshotAfterTakingSnapshot = 
SnapshotInfo.BackupSnapshotAfterTakingSnapshot.value();
 
     private List<Integer> runningAndAllocatedVmUsageTypes = 
Arrays.asList(UsageTypes.RUNNING_VM, UsageTypes.ALLOCATED_VM);
@@ -778,6 +783,19 @@ public class PresetVariableHelper {
         value.setId(network.getUuid());
         value.setName(network.getName());
         value.setState(usageRecord.getState());
+
+        
value.setNetworkOffering(getPresetVariableValueNetworkOffering(network.getNetworkOfferingId()));
+    }
+
+    protected GenericPresetVariable getPresetVariableValueNetworkOffering(Long 
networkOfferingId) {
+        NetworkOfferingVO networkOfferingVo = 
networkOfferingDao.findByIdIncludingRemoved(networkOfferingId);
+        validateIfObjectIsNull(networkOfferingVo, networkOfferingId, "network 
offering");
+
+        GenericPresetVariable networkOffering = new GenericPresetVariable();
+        networkOffering.setId(networkOfferingVo.getUuid());
+        networkOffering.setName(networkOfferingVo.getName());
+
+        return networkOffering;
     }
 
     protected void loadPresetVariableValueForVpc(UsageVO usageRecord, Value 
value) {
@@ -793,6 +811,18 @@ public class PresetVariableHelper {
 
         value.setId(vpc.getUuid());
         value.setName(vpc.getName());
+        
value.setVpcOffering(getPresetVariableValueVpcOffering(vpc.getVpcOfferingId()));
+    }
+
+    protected GenericPresetVariable getPresetVariableValueVpcOffering(Long 
vpcOfferingId) {
+        VpcOfferingVO vpcOfferingVo = 
vpcOfferingDao.findByIdIncludingRemoved(vpcOfferingId);
+        validateIfObjectIsNull(vpcOfferingVo, vpcOfferingId, "vpc offering");
+
+        GenericPresetVariable vpcOffering = new GenericPresetVariable();
+        vpcOffering.setId(vpcOfferingVo.getUuid());
+        vpcOffering.setName(vpcOfferingVo.getName());
+
+        return vpcOffering;
     }
 
     /**
diff --git 
a/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/Value.java
 
b/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/Value.java
index ac776d13c57..aff2c040e74 100644
--- 
a/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/Value.java
+++ 
b/framework/quota/src/main/java/org/apache/cloudstack/quota/activationrule/presetvariables/Value.java
@@ -96,6 +96,12 @@ public class Value extends GenericPresetVariable {
 
     private String state;
 
+    @PresetVariableDefinition(description = "Network offering of the 
network.", supportedTypes = {QuotaTypes.NETWORK})
+    private GenericPresetVariable networkOffering;
+
+    @PresetVariableDefinition(description = "VPC offering of the VPC.", 
supportedTypes = {QuotaTypes.VPC})
+    private GenericPresetVariable vpcOffering;
+
     public Host getHost() {
         return host;
     }
@@ -255,4 +261,20 @@ public class Value extends GenericPresetVariable {
     public void setState(String state) {
         this.state = state;
     }
+
+    public GenericPresetVariable getNetworkOffering() {
+        return networkOffering;
+    }
+
+    public void setNetworkOffering(GenericPresetVariable networkOffering) {
+        this.networkOffering = networkOffering;
+    }
+
+    public GenericPresetVariable getVpcOffering() {
+        return vpcOffering;
+    }
+
+    public void setVpcOffering(GenericPresetVariable vpcOffering) {
+        this.vpcOffering = vpcOffering;
+    }
 }
diff --git 
a/framework/quota/src/test/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelperTest.java
 
b/framework/quota/src/test/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelperTest.java
index 85397503587..fb093a45679 100644
--- 
a/framework/quota/src/test/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelperTest.java
+++ 
b/framework/quota/src/test/java/org/apache/cloudstack/quota/activationrule/presetvariables/PresetVariableHelperTest.java
@@ -31,6 +31,10 @@ import com.cloud.dc.ClusterDetailsDao;
 import com.cloud.dc.ClusterDetailsVO;
 import com.cloud.host.HostTagVO;
 import com.cloud.hypervisor.Hypervisor;
+import com.cloud.network.dao.NetworkVO;
+import com.cloud.network.vpc.VpcOfferingVO;
+import com.cloud.network.vpc.VpcVO;
+import com.cloud.network.vpc.dao.VpcOfferingDao;
 import com.cloud.storage.StoragePoolTagVO;
 import org.apache.cloudstack.acl.RoleType;
 import org.apache.cloudstack.acl.RoleVO;
@@ -38,7 +42,9 @@ import org.apache.cloudstack.acl.dao.RoleDao;
 import org.apache.cloudstack.backup.BackupOfferingVO;
 import org.apache.cloudstack.backup.dao.BackupOfferingDao;
 import org.apache.cloudstack.quota.constant.QuotaTypes;
+import org.apache.cloudstack.quota.dao.NetworkDao;
 import org.apache.cloudstack.quota.dao.VmTemplateDao;
+import org.apache.cloudstack.quota.dao.VpcDao;
 import org.apache.cloudstack.storage.datastore.db.ImageStoreDao;
 import org.apache.cloudstack.storage.datastore.db.ImageStoreVO;
 import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
@@ -188,6 +194,15 @@ public class PresetVariableHelperTest {
     @Mock
     BackupOfferingDao backupOfferingDaoMock;
 
+    @Mock
+    NetworkDao networkDaoMock;
+
+    @Mock
+    VpcDao vpcDaoMock;
+
+    @Mock
+    VpcOfferingDao vpcOfferingDaoMock;
+
     List<Integer> runningAndAllocatedVmUsageTypes = 
Arrays.asList(UsageTypes.RUNNING_VM, UsageTypes.ALLOCATED_VM);
     List<Integer> templateAndIsoUsageTypes = 
Arrays.asList(UsageTypes.TEMPLATE, UsageTypes.ISO);
 
@@ -223,6 +238,8 @@ public class PresetVariableHelperTest {
         value.setVmSnapshotType(VMSnapshot.Type.Disk.toString());
         value.setComputingResources(getComputingResourcesForTests());
         value.setVolumeType(Volume.Type.DATADISK.toString());
+        value.setNetworkOffering(getNetworkOfferingForTests());
+        value.setVpcOffering(getVpcOfferingForTests());
         return value;
     }
 
@@ -324,6 +341,20 @@ public class PresetVariableHelperTest {
         return diskOffering;
     }
 
+    private GenericPresetVariable getNetworkOfferingForTests() {
+        GenericPresetVariable networkOffering = new GenericPresetVariable();
+        networkOffering.setId("network_offering_id");
+        networkOffering.setName("network_offering_name");
+        return networkOffering;
+    }
+
+    private GenericPresetVariable getVpcOfferingForTests() {
+        GenericPresetVariable vpcOffering = new GenericPresetVariable();
+        vpcOffering.setId("vpc_offering_id");
+        vpcOffering.setName("vpc_offering_name");
+        return vpcOffering;
+    }
+
     private void mockMethodValidateIfObjectIsNull() {
         
Mockito.doNothing().when(presetVariableHelperSpy).validateIfObjectIsNull(Mockito.any(),
 Mockito.anyLong(), Mockito.anyString());
     }
@@ -1289,4 +1320,100 @@ public class PresetVariableHelperTest {
         Mockito.when(imageStoreDaoMock.findById(1L)).thenReturn(store);
         
Assert.assertNotNull(presetVariableHelperSpy.getSnapshotImageStoreRef(1L, 1L));
     }
+
+    @Test
+    public void 
loadPresetVariableValueForNetworkTestRecordIsNotANetworkDoNothing() {
+        getQuotaTypesForTests(UsageTypes.NETWORK).forEach(type -> {
+            Mockito.doReturn(type.getKey()).when(usageVoMock).getUsageType();
+            
presetVariableHelperSpy.loadPresetVariableValueForNetwork(usageVoMock, null);
+        });
+
+        Mockito.verifyNoInteractions(networkDaoMock);
+    }
+
+    @Test
+    public void 
loadPresetVariableValueForNetworkTestRecordIsNetworkSetFields() {
+        Value expected = getValueForTests();
+
+        NetworkVO networkVoMock = Mockito.mock(NetworkVO.class);
+        
Mockito.doReturn(networkVoMock).when(networkDaoMock).findByIdIncludingRemoved(Mockito.anyLong());
+
+        mockMethodValidateIfObjectIsNull();
+
+        Mockito.doReturn(expected.getId()).when(networkVoMock).getUuid();
+        Mockito.doReturn(expected.getName()).when(networkVoMock).getName();
+        Mockito.doReturn(expected.getState()).when(usageVoMock).getState();
+        
Mockito.doReturn(expected.getNetworkOffering()).when(presetVariableHelperSpy).getPresetVariableValueNetworkOffering(Mockito.anyLong());
+
+        Mockito.doReturn(UsageTypes.NETWORK).when(usageVoMock).getUsageType();
+
+        Value result = new Value();
+        presetVariableHelperSpy.loadPresetVariableValueForNetwork(usageVoMock, 
result);
+
+        assertPresetVariableIdAndName(expected, result);
+        Assert.assertEquals(expected.getState(), result.getState());
+        Assert.assertEquals(expected.getNetworkOffering(), 
result.getNetworkOffering());
+    }
+
+    @Test
+    public void loadPresetVariableValueForVpcTestRecordIsNotAVpcDoNothing() {
+        getQuotaTypesForTests(UsageTypes.VPC).forEach(type -> {
+            Mockito.doReturn(type.getKey()).when(usageVoMock).getUsageType();
+            presetVariableHelperSpy.loadPresetVariableValueForVpc(usageVoMock, 
null);
+        });
+
+        Mockito.verifyNoInteractions(networkDaoMock);
+    }
+
+    @Test
+    public void loadPresetVariableValueForVpcTestRecordIsVpcSetFields() {
+        Value expected = getValueForTests();
+
+        VpcVO networkVoMock = Mockito.mock(VpcVO.class);
+        
Mockito.doReturn(networkVoMock).when(vpcDaoMock).findByIdIncludingRemoved(Mockito.anyLong());
+
+        mockMethodValidateIfObjectIsNull();
+
+        Mockito.doReturn(expected.getId()).when(networkVoMock).getUuid();
+        Mockito.doReturn(expected.getName()).when(networkVoMock).getName();
+        
Mockito.doReturn(expected.getVpcOffering()).when(presetVariableHelperSpy).getPresetVariableValueVpcOffering(Mockito.anyLong());
+
+        Mockito.doReturn(UsageTypes.VPC).when(usageVoMock).getUsageType();
+
+        Value result = new Value();
+        presetVariableHelperSpy.loadPresetVariableValueForVpc(usageVoMock, 
result);
+
+        assertPresetVariableIdAndName(expected, result);
+        Assert.assertEquals(expected.getVpcOffering(), 
result.getVpcOffering());
+    }
+
+    @Test
+    public void 
getPresetVariableValueNetworkOfferingTestSetValuesAndReturnObject() {
+        NetworkOfferingVO networkOfferingVoMock = 
Mockito.mock(NetworkOfferingVO.class);
+        
Mockito.doReturn(networkOfferingVoMock).when(networkOfferingDaoMock).findByIdIncludingRemoved(Mockito.anyLong());
+        mockMethodValidateIfObjectIsNull();
+
+        GenericPresetVariable expected = getGenericPresetVariableForTests();
+        
Mockito.doReturn(expected.getId()).when(networkOfferingVoMock).getUuid();
+        
Mockito.doReturn(expected.getName()).when(networkOfferingVoMock).getName();
+
+        GenericPresetVariable result = 
presetVariableHelperSpy.getPresetVariableValueNetworkOffering(1L);
+
+        assertPresetVariableIdAndName(expected, result);
+    }
+
+    @Test
+    public void 
getPresetVariableValueVpcOfferingTestSetValuesAndReturnObject() {
+        VpcOfferingVO vpcOfferingVoMock = Mockito.mock(VpcOfferingVO.class);
+        
Mockito.doReturn(vpcOfferingVoMock).when(vpcOfferingDaoMock).findByIdIncludingRemoved(Mockito.anyLong());
+        mockMethodValidateIfObjectIsNull();
+
+        GenericPresetVariable expected = getGenericPresetVariableForTests();
+        Mockito.doReturn(expected.getId()).when(vpcOfferingVoMock).getUuid();
+        Mockito.doReturn(expected.getName()).when(vpcOfferingVoMock).getName();
+
+        GenericPresetVariable result = 
presetVariableHelperSpy.getPresetVariableValueVpcOffering(1L);
+
+        assertPresetVariableIdAndName(expected, result);
+    }
 }

Reply via email to