cloudstack-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From kous...@apache.org
Subject [1/2] git commit: updated refs/heads/master to bc86bae
Date Tue, 10 Jan 2017 09:29:47 GMT
Repository: cloudstack
Updated Branches:
  refs/heads/master 57db64717 -> bc86baeaa


CLOUDSTACK-9650: Allow starting VMs regardless of cpu/memory cluster.disablethreshold setting
Introduced a global configuration flag 'cluster.threshold.enabled'. By default the flag is
true.
If the value is false, then a VM can be started in a cluster even if the cluster thresholds
are
crossed. However, for a new VM deployment the cluster threshold will always be honoured.


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/97ffe071
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/97ffe071
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/97ffe071

Branch: refs/heads/master
Commit: 97ffe0711ec3abbadda01b1c92ca050fe4cac59e
Parents: a2e65ac
Author: Koushik Das <koushik@apache.org>
Authored: Fri Dec 2 23:08:32 2016 +0530
Committer: Koushik Das <koushik@apache.org>
Committed: Fri Dec 2 23:08:32 2016 +0530

----------------------------------------------------------------------
 .../cloud/deploy/DeploymentClusterPlanner.java  | 10 +++
 .../com/cloud/vm/VirtualMachineManagerImpl.java |  7 ++
 .../implicitplanner/ImplicitPlannerTest.java    |  8 +++
 .../src/com/cloud/deploy/FirstFitPlanner.java   | 20 +++++-
 server/src/com/cloud/vm/UserVmManagerImpl.java  |  1 +
 .../vm/DeploymentPlanningManagerImplTest.java   | 11 +++
 .../test/com/cloud/vm/FirstFitPlannerTest.java  | 76 +++++++++++++++++++-
 7 files changed, 129 insertions(+), 4 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/api/src/com/cloud/deploy/DeploymentClusterPlanner.java
----------------------------------------------------------------------
diff --git a/api/src/com/cloud/deploy/DeploymentClusterPlanner.java b/api/src/com/cloud/deploy/DeploymentClusterPlanner.java
index 6c09a6d..c2f0776 100644
--- a/api/src/com/cloud/deploy/DeploymentClusterPlanner.java
+++ b/api/src/com/cloud/deploy/DeploymentClusterPlanner.java
@@ -29,6 +29,7 @@ public interface DeploymentClusterPlanner extends DeploymentPlanner {
 
     static final String ClusterCPUCapacityDisableThresholdCK = "cluster.cpu.allocated.capacity.disablethreshold";
     static final String ClusterMemoryCapacityDisableThresholdCK = "cluster.memory.allocated.capacity.disablethreshold";
+    static final String ClusterThresholdEnabledCK = "cluster.threshold.enabled";
 
     static final ConfigKey<Float> ClusterCPUCapacityDisableThreshold =
         new ConfigKey<Float>(
@@ -46,6 +47,15 @@ public interface DeploymentClusterPlanner extends DeploymentPlanner {
             "0.85",
             "Percentage (as a value between 0 and 1) of memory utilization above which allocators
will disable using the cluster for low memory available. Keep the corresponding notification
threshold lower than this to be notified beforehand.",
             true, ConfigKey.Scope.Cluster, null);
+    static final ConfigKey<Boolean> ClusterThresholdEnabled =
+        new ConfigKey<Boolean>(
+            "Advanced",
+            Boolean.class,
+            ClusterThresholdEnabledCK,
+            "true",
+            "Enable/Disable cluster thresholds. If disabled, an instance can start in a cluster
even though the threshold may be crossed.",
+            false,
+            ConfigKey.Scope.Zone);
 
     /**
      * This is called to determine list of possible clusters where a virtual

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java
----------------------------------------------------------------------
diff --git a/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java b/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java
index 99693ba..e1ce697 100644
--- a/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java
+++ b/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java
@@ -1052,6 +1052,13 @@ public class VirtualMachineManagerImpl extends ManagerBase implements
VirtualMac
                                 _resourceMgr.updateGPUDetails(destHostId, gpuDevice.getGroupDetails());
                             }
 
+                            // Remove the information on whether it was a deploy vm request.The
deployvm=true information
+                            // is set only when the vm is being deployed. When a vm is started
from a stop state the
+                            // information isn't set,
+                            if (_uservmDetailsDao.findDetail(vm.getId(), "deployvm") != null)
{
+                                _uservmDetailsDao.removeDetail(vm.getId(), "deployvm");
+                            }
+
                             startedVm = vm;
                             if (s_logger.isDebugEnabled()) {
                                 s_logger.debug("Start completed for VM " + vm);

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/plugins/deployment-planners/implicit-dedication/test/org/apache/cloudstack/implicitplanner/ImplicitPlannerTest.java
----------------------------------------------------------------------
diff --git a/plugins/deployment-planners/implicit-dedication/test/org/apache/cloudstack/implicitplanner/ImplicitPlannerTest.java
b/plugins/deployment-planners/implicit-dedication/test/org/apache/cloudstack/implicitplanner/ImplicitPlannerTest.java
index 754f36e..79cb1b4 100644
--- a/plugins/deployment-planners/implicit-dedication/test/org/apache/cloudstack/implicitplanner/ImplicitPlannerTest.java
+++ b/plugins/deployment-planners/implicit-dedication/test/org/apache/cloudstack/implicitplanner/ImplicitPlannerTest.java
@@ -94,6 +94,7 @@ import com.cloud.vm.UserVmVO;
 import com.cloud.vm.VMInstanceVO;
 import com.cloud.vm.VirtualMachineProfileImpl;
 import com.cloud.vm.dao.UserVmDao;
+import com.cloud.vm.dao.UserVmDetailsDao;
 import com.cloud.vm.dao.VMInstanceDao;
 
 @RunWith(SpringJUnit4ClassRunner.class)
@@ -121,6 +122,8 @@ public class ImplicitPlannerTest {
     @Inject
     UserVmDao vmDao;
     @Inject
+    UserVmDetailsDao vmDetailsDao;
+    @Inject
     VMInstanceDao vmInstanceDao;
     @Inject
     VolumeDao volsDao;
@@ -521,6 +524,11 @@ public class ImplicitPlannerTest {
         }
 
         @Bean
+        public UserVmDetailsDao userVmDetailsDao() {
+            return Mockito.mock(UserVmDetailsDao.class);
+        }
+
+        @Bean
         public VMInstanceDao vmInstanceDao() {
             return Mockito.mock(VMInstanceDao.class);
         }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/server/src/com/cloud/deploy/FirstFitPlanner.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/deploy/FirstFitPlanner.java b/server/src/com/cloud/deploy/FirstFitPlanner.java
index 640834b..c3df417 100644
--- a/server/src/com/cloud/deploy/FirstFitPlanner.java
+++ b/server/src/com/cloud/deploy/FirstFitPlanner.java
@@ -66,6 +66,7 @@ import com.cloud.utils.component.AdapterBase;
 import com.cloud.vm.VirtualMachine;
 import com.cloud.vm.VirtualMachineProfile;
 import com.cloud.vm.dao.UserVmDao;
+import com.cloud.vm.dao.UserVmDetailsDao;
 import com.cloud.vm.dao.VMInstanceDao;
 
 public class FirstFitPlanner extends AdapterBase implements DeploymentClusterPlanner, Configurable,
DeploymentPlanner {
@@ -89,6 +90,8 @@ public class FirstFitPlanner extends AdapterBase implements DeploymentClusterPla
     @Inject
     protected UserVmDao vmDao;
     @Inject
+    protected UserVmDetailsDao vmDetailsDao;
+    @Inject
     protected VMInstanceDao vmInstanceDao;
     @Inject
     protected VolumeDao volsDao;
@@ -309,6 +312,16 @@ public class FirstFitPlanner extends AdapterBase implements DeploymentClusterPla
     protected void removeClustersCrossingThreshold(List<Long> clusterListForVmAllocation,
ExcludeList avoid,
             VirtualMachineProfile vmProfile, DeploymentPlan plan) {
 
+        // Check if cluster threshold for cpu/memory has to be checked or not. By default
we
+        // always check cluster threshold isn't crossed. However, the check may be skipped
for
+        // starting (not deploying) an instance.
+        VirtualMachine vm = vmProfile.getVirtualMachine();
+        Map<String, String> details = vmDetailsDao.listDetailsKeyPairs(vm.getId());
+        Boolean isThresholdEnabled = ClusterThresholdEnabled.value();
+        if (!(isThresholdEnabled || (details != null && details.containsKey("deployvm"))))
{
+            return;
+        }
+
         List<Short> capacityList = getCapacitiesForCheckingThreshold();
         List<Long> clustersCrossingThreshold = new ArrayList<Long>();
 
@@ -323,12 +336,13 @@ public class FirstFitPlanner extends AdapterBase implements DeploymentClusterPla
             if (clusterListForVmAllocation == null || clusterListForVmAllocation.size() ==
0) {
                 return;
             }
+
             if (capacity == Capacity.CAPACITY_TYPE_CPU) {
                 clustersCrossingThreshold =
- capacityDao.listClustersCrossingThreshold(capacity, plan.getDataCenterId(), ClusterCPUCapacityDisableThreshold.key(),
cpu_requested);
+                        capacityDao.listClustersCrossingThreshold(capacity, plan.getDataCenterId(),
ClusterCPUCapacityDisableThreshold.key(), cpu_requested);
             } else if (capacity == Capacity.CAPACITY_TYPE_MEMORY) {
                 clustersCrossingThreshold =
- capacityDao.listClustersCrossingThreshold(capacity, plan.getDataCenterId(), ClusterMemoryCapacityDisableThreshold.key(),
ram_requested);
+                        capacityDao.listClustersCrossingThreshold(capacity, plan.getDataCenterId(),
ClusterMemoryCapacityDisableThreshold.key(), ram_requested);
             }
 
             if (clustersCrossingThreshold != null && clustersCrossingThreshold.size()
!= 0) {
@@ -565,6 +579,6 @@ public class FirstFitPlanner extends AdapterBase implements DeploymentClusterPla
 
     @Override
     public ConfigKey<?>[] getConfigKeys() {
-        return new ConfigKey<?>[] {ClusterCPUCapacityDisableThreshold, ClusterMemoryCapacityDisableThreshold};
+        return new ConfigKey<?>[] {ClusterCPUCapacityDisableThreshold, ClusterMemoryCapacityDisableThreshold,
ClusterThresholdEnabled};
     }
 }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/server/src/com/cloud/vm/UserVmManagerImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/vm/UserVmManagerImpl.java b/server/src/com/cloud/vm/UserVmManagerImpl.java
index 17cbbde..d60b8c1 100644
--- a/server/src/com/cloud/vm/UserVmManagerImpl.java
+++ b/server/src/com/cloud/vm/UserVmManagerImpl.java
@@ -3582,6 +3582,7 @@ public class UserVmManagerImpl extends ManagerBase implements UserVmManager,
Vir
                 for (String key : customParameters.keySet()) {
                     vm.setDetail(key, customParameters.get(key));
                 }
+                vm.setDetail("deployvm", "true");
                 _vmDao.saveDetails(vm);
 
                 s_logger.debug("Allocating in the DB for vm");

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/server/test/com/cloud/vm/DeploymentPlanningManagerImplTest.java
----------------------------------------------------------------------
diff --git a/server/test/com/cloud/vm/DeploymentPlanningManagerImplTest.java b/server/test/com/cloud/vm/DeploymentPlanningManagerImplTest.java
index 72960e3..2e87817 100644
--- a/server/test/com/cloud/vm/DeploymentPlanningManagerImplTest.java
+++ b/server/test/com/cloud/vm/DeploymentPlanningManagerImplTest.java
@@ -94,6 +94,7 @@ import com.cloud.storage.dao.VolumeDao;
 import com.cloud.user.AccountManager;
 import com.cloud.utils.component.ComponentContext;
 import com.cloud.vm.dao.UserVmDao;
+import com.cloud.vm.dao.UserVmDetailsDao;
 import com.cloud.vm.dao.VMInstanceDao;
 
 @RunWith(SpringJUnit4ClassRunner.class)
@@ -130,6 +131,9 @@ public class DeploymentPlanningManagerImplTest {
     @Inject
     DedicatedResourceDao _dedicatedDao;
 
+    @Inject
+    UserVmDetailsDao vmDetailsDao;
+
     private static long domainId = 5L;
 
     private static long dataCenterId = 1L;
@@ -150,6 +154,8 @@ public class DeploymentPlanningManagerImplTest {
         VMInstanceVO vm = new VMInstanceVO();
         Mockito.when(vmProfile.getVirtualMachine()).thenReturn(vm);
 
+        Mockito.when(vmDetailsDao.listDetailsKeyPairs(Matchers.anyLong())).thenReturn(null);
+
         Mockito.when(_dcDao.findById(Matchers.anyLong())).thenReturn(dc);
         Mockito.when(dc.getId()).thenReturn(dataCenterId);
 
@@ -383,6 +389,11 @@ public class DeploymentPlanningManagerImplTest {
         }
 
         @Bean
+        public UserVmDetailsDao userVmDetailsDao() {
+            return Mockito.mock(UserVmDetailsDao.class);
+        }
+
+        @Bean
         public VMInstanceDao vmInstanceDao() {
             return Mockito.mock(VMInstanceDao.class);
         }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/97ffe071/server/test/com/cloud/vm/FirstFitPlannerTest.java
----------------------------------------------------------------------
diff --git a/server/test/com/cloud/vm/FirstFitPlannerTest.java b/server/test/com/cloud/vm/FirstFitPlannerTest.java
index b7b103b..41dd8c0 100644
--- a/server/test/com/cloud/vm/FirstFitPlannerTest.java
+++ b/server/test/com/cloud/vm/FirstFitPlannerTest.java
@@ -32,7 +32,12 @@ import javax.inject.Inject;
 
 import org.apache.cloudstack.context.CallContext;
 import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreManager;
+import org.apache.cloudstack.framework.config.ConfigDepot;
+import org.apache.cloudstack.framework.config.ConfigKey;
+import org.apache.cloudstack.framework.config.ScopedConfigStorage;
 import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
+import org.apache.cloudstack.framework.config.impl.ConfigDepotImpl;
+import org.apache.cloudstack.framework.config.impl.ConfigurationVO;
 import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
 import org.apache.cloudstack.test.utils.SpringUtils;
 import org.junit.After;
@@ -63,6 +68,7 @@ import com.cloud.dc.dao.ClusterDao;
 import com.cloud.dc.dao.DataCenterDao;
 import com.cloud.dc.dao.HostPodDao;
 import com.cloud.deploy.DataCenterDeployment;
+import com.cloud.deploy.DeploymentClusterPlanner;
 import com.cloud.deploy.DeploymentPlanner.ExcludeList;
 import com.cloud.deploy.FirstFitPlanner;
 import com.cloud.exception.InsufficientServerCapacityException;
@@ -86,6 +92,7 @@ import com.cloud.user.AccountVO;
 import com.cloud.utils.Pair;
 import com.cloud.utils.component.ComponentContext;
 import com.cloud.vm.dao.UserVmDao;
+import com.cloud.vm.dao.UserVmDetailsDao;
 import com.cloud.vm.dao.VMInstanceDao;
 
 @RunWith(SpringJUnit4ClassRunner.class)
@@ -101,6 +108,8 @@ public class FirstFitPlannerTest {
     @Inject
     UserVmDao vmDao;
     @Inject
+    UserVmDetailsDao vmDetailsDao;
+    @Inject
     ConfigurationDao configDao;
     @Inject
     CapacityDao capacityDao;
@@ -114,6 +123,10 @@ public class FirstFitPlannerTest {
     HostGpuGroupsDao hostGpuGroupsDao;
     @Inject
     HostTagsDao hostTagsDao;
+    @Inject
+    ConfigDepotImpl configDepot;
+    @Inject
+    ScopedConfigStorage scopedStorage;
 
     private static long domainId = 1L;
     long dataCenterId = 1L;
@@ -126,6 +139,8 @@ public class FirstFitPlannerTest {
 
     @Before
     public void setUp() {
+        ConfigKey.init(configDepot);
+
         when(configDao.getValue(Mockito.anyString())).thenReturn(null);
         when(configDao.getValue(Config.ImplicitHostTags.key())).thenReturn("GPU");
 
@@ -138,6 +153,7 @@ public class FirstFitPlannerTest {
 
     @After
     public void tearDown() {
+        ConfigKey.init(null);
         CallContext.unregister();
     }
 
@@ -157,7 +173,50 @@ public class FirstFitPlannerTest {
         reorderedClusterList.add(6L);
         reorderedClusterList.add(2L);
 
-        assertTrue("Reordered cluster list is not ownering the implict host tags", (clusterList.equals(reorderedClusterList)));
+        assertTrue("Reordered cluster list is not honoring the implict host tags", (clusterList.equals(reorderedClusterList)));
+    }
+
+    @Test
+    public void checkClusterReorderingForDeployVMWithThresholdCheckDisabled() throws InsufficientServerCapacityException
{
+        VirtualMachineProfileImpl vmProfile = mock(VirtualMachineProfileImpl.class);
+        DataCenterDeployment plan = mock(DataCenterDeployment.class);
+        ExcludeList avoids = mock(ExcludeList.class);
+        initializeForTest(vmProfile, plan, avoids);
+        List<Long> clustersCrossingThreshold = initializeForClusterThresholdDisabled();
+
+        Map<String, String> details = new HashMap<String, String>();
+        details.put("deployvm", "true");
+        when(vmDetailsDao.listDetailsKeyPairs(vmProfile.getVirtualMachine().getId())).thenReturn(details);
+
+        List<Long> clusterList = planner.orderClusters(vmProfile, plan, avoids);
+        assertTrue("Reordered cluster list have clusters exceeding threshold", (!clusterList.containsAll(clustersCrossingThreshold)));
+    }
+
+    @Test
+    public void checkClusterReorderingForStartVMWithThresholdCheckDisabled() throws InsufficientServerCapacityException
{
+        VirtualMachineProfileImpl vmProfile = mock(VirtualMachineProfileImpl.class);
+        DataCenterDeployment plan = mock(DataCenterDeployment.class);
+        ExcludeList avoids = mock(ExcludeList.class);
+        initializeForTest(vmProfile, plan, avoids);
+        List<Long> clustersCrossingThreshold = initializeForClusterThresholdDisabled();
+
+        List<Long> clusterList = planner.orderClusters(vmProfile, plan, avoids);
+        assertTrue("Reordered cluster list does not have clusters exceeding threshold", (clusterList.containsAll(clustersCrossingThreshold)));
+    }
+
+    private List<Long> initializeForClusterThresholdDisabled() {
+        when(configDepot.global()).thenReturn(configDao);
+
+        ConfigurationVO config = mock(ConfigurationVO.class);
+        when(config.getValue()).thenReturn(String.valueOf(false));
+        when(configDao.findById(DeploymentClusterPlanner.ClusterThresholdEnabled.key())).thenReturn(config);
+
+        List<Long> clustersCrossingThreshold = new ArrayList<Long>();
+        clustersCrossingThreshold.add(3L);
+        when(capacityDao.listClustersCrossingThreshold(
+                Mockito.anyShort(), Mockito.anyLong(), Mockito.anyString(), Mockito.anyLong())).thenReturn(clustersCrossingThreshold);
+
+        return clustersCrossingThreshold;
     }
 
     private void initializeForTest(VirtualMachineProfileImpl vmProfile, DataCenterDeployment
plan, ExcludeList avoids) {
@@ -312,6 +371,11 @@ public class FirstFitPlannerTest {
         }
 
         @Bean
+        public UserVmDetailsDao userVmDetailsDao() {
+            return Mockito.mock(UserVmDetailsDao.class);
+        }
+
+        @Bean
         public VMInstanceDao vmInstanceDao() {
             return Mockito.mock(VMInstanceDao.class);
         }
@@ -376,6 +440,16 @@ public class FirstFitPlannerTest {
             return Mockito.mock(ResourceManager.class);
         }
 
+        @Bean
+        public ConfigDepot configDepot() {
+            return Mockito.mock(ConfigDepotImpl.class);
+        }
+
+        @Bean
+        public ScopedConfigStorage configStorage() {
+            return Mockito.mock(ScopedConfigStorage.class);
+        }
+
         public static class Library implements TypeFilter {
             @Override
             public boolean match(MetadataReader mdr, MetadataReaderFactory arg1) throws IOException
{


Mime
View raw message