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

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


The following commit(s) were added to refs/heads/master by this push:
     new 4c60a5b  Fix slow vm creation when large sf snapshot count (#3282)
4c60a5b is described below

commit 4c60a5b1ff39b49171d59738c72cf217789b049a
Author: skattoju4 <[email protected]>
AuthorDate: Sat May 11 10:02:52 2019 -0400

    Fix slow vm creation when large sf snapshot count (#3282)
    
    * skip geting used bytes for volumes that are not in Ready state
    * updated log message
    * filter snapshots by state backedup
    * removed * import
    * filter templates by state 'DOWNLOADED'
    * refactored getUsedBytes to use O(1) queries
    * querying for ready volumes instead filtering in memory
    * make listByStoreIdInReadyState more generic ex listByStoreIdAndState
    * updated snapshot search criteria for listByStoreIdAndState
    * updated template search criteria for listByPoolIdAndState
    * fixed typo in search criteria for listByTemplateAndState
    * fixed typo in search criteria for templates in listByPoolIdAndState
---
 .../com/cloud/storage/dao/VMTemplatePoolDao.java   |  2 +
 .../cloud/storage/dao/VMTemplatePoolDaoImpl.java   | 18 +++++-
 .../main/java/com/cloud/storage/dao/VolumeDao.java |  2 +
 .../java/com/cloud/storage/dao/VolumeDaoImpl.java  |  8 +++
 .../storage/datastore/db/SnapshotDataStoreDao.java |  2 +
 .../storage/image/db/SnapshotDataStoreDaoImpl.java | 18 +++++-
 .../driver/SolidFirePrimaryDataStoreDriver.java    | 70 ++++++----------------
 7 files changed, 66 insertions(+), 54 deletions(-)

diff --git 
a/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDao.java 
b/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDao.java
index 520416e..6216ef7 100644
--- a/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDao.java
+++ b/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDao.java
@@ -33,6 +33,8 @@ public interface VMTemplatePoolDao extends 
GenericDao<VMTemplateStoragePoolVO, L
 
     public VMTemplateStoragePoolVO findByPoolTemplate(long poolId, long 
templateId);
 
+    public List<VMTemplateStoragePoolVO> listByPoolIdAndState(long poolId, 
ObjectInDataStoreStateMachine.State state);
+
     public List<VMTemplateStoragePoolVO> listByTemplateStatus(long templateId, 
VMTemplateStoragePoolVO.Status downloadState);
 
     public List<VMTemplateStoragePoolVO> listByTemplateStatus(long templateId, 
VMTemplateStoragePoolVO.Status downloadState, long poolId);
diff --git 
a/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDaoImpl.java 
b/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDaoImpl.java
index d2c4a99..bb3985f 100644
--- 
a/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDaoImpl.java
+++ 
b/engine/schema/src/main/java/com/cloud/storage/dao/VMTemplatePoolDaoImpl.java
@@ -24,11 +24,13 @@ import java.util.List;
 
 
 import javax.inject.Inject;
+
+import org.apache.cloudstack.engine.subsystem.api.storage.DataObjectInStore;
 import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreManager;
+import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine;
 import org.apache.log4j.Logger;
 import org.springframework.stereotype.Component;
 
-import org.apache.cloudstack.engine.subsystem.api.storage.DataObjectInStore;
 import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine.Event;
 import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine.State;
 
@@ -55,6 +57,7 @@ public class VMTemplatePoolDaoImpl extends 
GenericDaoBase<VMTemplateStoragePoolV
     protected final SearchBuilder<VMTemplateStoragePoolVO> 
TemplateStatusSearch;
     protected final SearchBuilder<VMTemplateStoragePoolVO> 
TemplatePoolStatusSearch;
     protected final SearchBuilder<VMTemplateStoragePoolVO> 
TemplateStatesSearch;
+    protected final SearchBuilder<VMTemplateStoragePoolVO> 
TemplatePoolStateSearch;
     protected final SearchBuilder<VMTemplateStoragePoolVO> updateStateSearch;
 
     protected static final String UPDATE_TEMPLATE_HOST_REF = "UPDATE 
template_spool_ref SET download_state = ?, download_pct= ?, last_updated = ? "
@@ -96,6 +99,11 @@ public class VMTemplatePoolDaoImpl extends 
GenericDaoBase<VMTemplateStoragePoolV
         TemplatePoolStatusSearch.and("download_state", 
TemplatePoolStatusSearch.entity().getDownloadState(), SearchCriteria.Op.EQ);
         TemplatePoolStatusSearch.done();
 
+        TemplatePoolStateSearch = createSearchBuilder();
+        TemplatePoolStateSearch.and("pool_id", 
TemplatePoolStateSearch.entity().getPoolId(), SearchCriteria.Op.EQ);
+        TemplatePoolStateSearch.and("state", 
TemplatePoolStateSearch.entity().getState(), SearchCriteria.Op.EQ);
+        TemplatePoolStateSearch.done();
+
         TemplateStatesSearch = createSearchBuilder();
         TemplateStatesSearch.and("template_id", 
TemplateStatesSearch.entity().getTemplateId(), SearchCriteria.Op.EQ);
         TemplateStatesSearch.and("states", 
TemplateStatesSearch.entity().getDownloadState(), SearchCriteria.Op.IN);
@@ -139,6 +147,14 @@ public class VMTemplatePoolDaoImpl extends 
GenericDaoBase<VMTemplateStoragePoolV
     }
 
     @Override
+    public List<VMTemplateStoragePoolVO> listByPoolIdAndState(long poolId, 
ObjectInDataStoreStateMachine.State state) {
+        SearchCriteria<VMTemplateStoragePoolVO> sc = 
TemplatePoolStateSearch.create();
+        sc.setParameters("pool_id", poolId);
+        sc.setParameters("state", state);
+        return listIncludingRemovedBy(sc);
+    }
+
+    @Override
     public List<VMTemplateStoragePoolVO> listByTemplateStatus(long templateId, 
VMTemplateStoragePoolVO.Status downloadState, long poolId) {
         SearchCriteria<VMTemplateStoragePoolVO> sc = 
TemplatePoolStatusSearch.create();
         sc.setParameters("pool_id", poolId);
diff --git a/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDao.java 
b/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDao.java
index 51d46a0..c0abb56 100644
--- a/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDao.java
+++ b/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDao.java
@@ -72,6 +72,8 @@ public interface VolumeDao extends GenericDao<VolumeVO, 
Long>, StateDao<Volume.S
 
     List<VolumeVO> findByPoolId(long poolId, Volume.Type volumeType);
 
+    List<VolumeVO> findByPoolIdAndState(long poolid, Volume.State state);
+
     List<VolumeVO> findByInstanceAndDeviceId(long instanceId, long deviceId);
 
     List<VolumeVO> findUsableVolumesForInstance(long instanceId);
diff --git 
a/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDaoImpl.java 
b/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDaoImpl.java
index 663a5f5..fb25c54 100644
--- a/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDaoImpl.java
+++ b/engine/schema/src/main/java/com/cloud/storage/dao/VolumeDaoImpl.java
@@ -149,6 +149,14 @@ public class VolumeDaoImpl extends 
GenericDaoBase<VolumeVO, Long> implements Vol
     }
 
     @Override
+    public List<VolumeVO> findByPoolIdAndState(long poolId, Volume.State 
state) {
+        SearchCriteria<VolumeVO> sc = AllFieldsSearch.create();
+        sc.setParameters("poolId", poolId);
+        sc.setParameters("state", state);
+        return listBy(sc);
+    }
+
+    @Override
     public List<VolumeVO> findCreatedByInstance(long id) {
         SearchCriteria<VolumeVO> sc = AllFieldsSearch.create();
         sc.setParameters("instanceId", id);
diff --git 
a/engine/schema/src/main/java/org/apache/cloudstack/storage/datastore/db/SnapshotDataStoreDao.java
 
b/engine/schema/src/main/java/org/apache/cloudstack/storage/datastore/db/SnapshotDataStoreDao.java
index 50f311a..819cb7b 100644
--- 
a/engine/schema/src/main/java/org/apache/cloudstack/storage/datastore/db/SnapshotDataStoreDao.java
+++ 
b/engine/schema/src/main/java/org/apache/cloudstack/storage/datastore/db/SnapshotDataStoreDao.java
@@ -30,6 +30,8 @@ StateDao<ObjectInDataStoreStateMachine.State, 
ObjectInDataStoreStateMachine.Even
 
     List<SnapshotDataStoreVO> listByStoreId(long id, DataStoreRole role);
 
+    List<SnapshotDataStoreVO> listByStoreIdAndState(long id, 
ObjectInDataStoreStateMachine.State state);
+
     List<SnapshotDataStoreVO> listActiveOnCache(long id);
 
     void deletePrimaryRecordsForStore(long id, DataStoreRole role);
diff --git 
a/engine/storage/src/main/java/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
 
b/engine/storage/src/main/java/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
index 6ca6b23..c7358d1 100644
--- 
a/engine/storage/src/main/java/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
+++ 
b/engine/storage/src/main/java/org/apache/cloudstack/storage/image/db/SnapshotDataStoreDaoImpl.java
@@ -27,6 +27,8 @@ import java.util.Map;
 import javax.inject.Inject;
 import javax.naming.ConfigurationException;
 
+import com.cloud.storage.DataStoreRole;
+import com.cloud.storage.SnapshotVO;
 import org.apache.cloudstack.engine.subsystem.api.storage.DataObjectInStore;
 import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine;
 import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine.Event;
@@ -37,8 +39,6 @@ import org.apache.log4j.Logger;
 import org.springframework.stereotype.Component;
 
 import com.cloud.hypervisor.Hypervisor;
-import com.cloud.storage.DataStoreRole;
-import com.cloud.storage.SnapshotVO;
 import com.cloud.storage.dao.SnapshotDao;
 import com.cloud.utils.db.DB;
 import com.cloud.utils.db.Filter;
@@ -54,6 +54,7 @@ public class SnapshotDataStoreDaoImpl extends 
GenericDaoBase<SnapshotDataStoreVO
     private static final Logger s_logger = 
Logger.getLogger(SnapshotDataStoreDaoImpl.class);
     private SearchBuilder<SnapshotDataStoreVO> updateStateSearch;
     private SearchBuilder<SnapshotDataStoreVO> storeSearch;
+    private SearchBuilder<SnapshotDataStoreVO> storeStateSearch;
     private SearchBuilder<SnapshotDataStoreVO> destroyedSearch;
     private SearchBuilder<SnapshotDataStoreVO> cacheSearch;
     private SearchBuilder<SnapshotDataStoreVO> snapshotSearch;
@@ -92,6 +93,11 @@ public class SnapshotDataStoreDaoImpl extends 
GenericDaoBase<SnapshotDataStoreVO
         storeSearch.and("state", storeSearch.entity().getState(), 
SearchCriteria.Op.NEQ);
         storeSearch.done();
 
+        storeStateSearch = createSearchBuilder();
+        storeStateSearch.and("store_id", 
storeStateSearch.entity().getDataStoreId(), SearchCriteria.Op.EQ);
+        storeStateSearch.and("state", storeStateSearch.entity().getState(), 
SearchCriteria.Op.EQ);
+        storeStateSearch.done();
+
         destroyedSearch = createSearchBuilder();
         destroyedSearch.and("store_id", 
destroyedSearch.entity().getDataStoreId(), SearchCriteria.Op.EQ);
         destroyedSearch.and("store_role", destroyedSearch.entity().getRole(), 
SearchCriteria.Op.EQ);
@@ -222,6 +228,14 @@ public class SnapshotDataStoreDaoImpl extends 
GenericDaoBase<SnapshotDataStoreVO
     }
 
     @Override
+    public List<SnapshotDataStoreVO> listByStoreIdAndState(long id, 
ObjectInDataStoreStateMachine.State state) {
+        SearchCriteria<SnapshotDataStoreVO> sc = storeStateSearch.create();
+        sc.setParameters("store_id", id);
+        sc.setParameters("state", state);
+        return listBy(sc);
+    }
+
+    @Override
     public void deletePrimaryRecordsForStore(long id, DataStoreRole role) {
         SearchCriteria<SnapshotDataStoreVO> sc = storeSearch.create();
         sc.setParameters("store_id", id);
diff --git 
a/plugins/storage/volume/solidfire/src/main/java/org/apache/cloudstack/storage/datastore/driver/SolidFirePrimaryDataStoreDriver.java
 
b/plugins/storage/volume/solidfire/src/main/java/org/apache/cloudstack/storage/datastore/driver/SolidFirePrimaryDataStoreDriver.java
index 370cdb0..19b678e 100644
--- 
a/plugins/storage/volume/solidfire/src/main/java/org/apache/cloudstack/storage/datastore/driver/SolidFirePrimaryDataStoreDriver.java
+++ 
b/plugins/storage/volume/solidfire/src/main/java/org/apache/cloudstack/storage/datastore/driver/SolidFirePrimaryDataStoreDriver.java
@@ -72,10 +72,13 @@ import 
org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo;
 import org.apache.cloudstack.engine.subsystem.api.storage.TemplateInfo;
 import org.apache.cloudstack.engine.subsystem.api.storage.VolumeDataFactory;
 import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
+import 
org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine;
 import org.apache.cloudstack.framework.async.AsyncCompletionCallback;
 import org.apache.cloudstack.storage.command.CommandResult;
 import org.apache.cloudstack.storage.command.CreateObjectAnswer;
 import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
+import org.apache.cloudstack.storage.datastore.db.SnapshotDataStoreDao;
+import org.apache.cloudstack.storage.datastore.db.SnapshotDataStoreVO;
 import org.apache.cloudstack.storage.datastore.db.StoragePoolDetailVO;
 import org.apache.cloudstack.storage.datastore.db.StoragePoolDetailsDao;
 import org.apache.cloudstack.storage.datastore.db.StoragePoolVO;
@@ -104,9 +107,10 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
     @Inject private HostDao hostDao;
     @Inject private SnapshotDao snapshotDao;
     @Inject private SnapshotDetailsDao snapshotDetailsDao;
+    @Inject private SnapshotDataStoreDao snapshotDataStoreDao;
     @Inject private PrimaryDataStoreDao storagePoolDao;
     @Inject private StoragePoolDetailsDao storagePoolDetailsDao;
-    @Inject private VMTemplatePoolDao tmpltPoolDao;
+    @Inject private VMTemplatePoolDao vmTemplatePoolDao;
     @Inject private VolumeDao volumeDao;
     @Inject private VolumeDetailsDao volumeDetailsDao;
     @Inject private VolumeDataFactory volumeFactory;
@@ -360,7 +364,7 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
     private long getUsedBytes(StoragePool storagePool, long volumeIdToIgnore) {
         long usedSpace = 0;
 
-        List<VolumeVO> lstVolumes = 
volumeDao.findByPoolId(storagePool.getId(), null);
+        List<VolumeVO> lstVolumes = 
volumeDao.findByPoolIdAndState(storagePool.getId(), Volume.State.Ready);
 
         if (lstVolumes != null) {
             for (VolumeVO volume : lstVolumes) {
@@ -368,62 +372,26 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
                     continue;
                 }
 
-                VolumeDetailVO volumeDetail = 
volumeDetailsDao.findDetail(volume.getId(), SolidFireUtil.VOLUME_SIZE);
+                usedSpace += 
getVolumeSizeIncludingHypervisorSnapshotReserve(volume.getSize(),volume.getHypervisorSnapshotReserve());
 
-                if (volumeDetail != null && volumeDetail.getValue() != null) {
-                    long volumeSize = Long.parseLong(volumeDetail.getValue());
-
-                    usedSpace += volumeSize;
-                }
-                else {
-                    SolidFireUtil.SolidFireConnection sfConnection = 
SolidFireUtil.getSolidFireConnection(storagePool.getId(), 
storagePoolDetailsDao);
-
-                    try {
-                        long lVolumeId = Long.parseLong(volume.getFolder());
-
-                        SolidFireUtil.SolidFireVolume sfVolume = 
SolidFireUtil.getVolume(sfConnection, lVolumeId);
-
-                        long volumeSize = sfVolume.getTotalSize();
-
-                        // SolidFireUtil.VOLUME_SIZE was introduced in 4.5.
-                        // To be backward compatible with releases prior to 
4.5, call updateVolumeDetails here.
-                        // That way if SolidFireUtil.VOLUME_SIZE wasn't put in 
the volume_details table when the
-                        // volume was initially created, it can be placed in 
volume_details here.
-                        updateVolumeDetails(volume.getId(), volumeSize, 
sfVolume.getScsiNaaDeviceId());
-
-                        usedSpace += volumeSize;
-                    }
-                    catch (Exception ex) {
-                        // can be ignored
-                    }
-                }
             }
         }
 
-        List<SnapshotVO> lstSnapshots = snapshotDao.listAll();
+        List<SnapshotDataStoreVO> snapshotDataStoreVOList = 
snapshotDataStoreDao.listByStoreIdAndState(storagePool.getId(), 
ObjectInDataStoreStateMachine.State.Ready);
 
-        if (lstSnapshots != null) {
-            for (SnapshotVO snapshot : lstSnapshots) {
-                SnapshotDetailsVO snapshotDetails = 
snapshotDetailsDao.findDetail(snapshot.getId(), SolidFireUtil.STORAGE_POOL_ID);
+        if (snapshotDataStoreVOList != null) {
+            for (SnapshotDataStoreVO snapshot : snapshotDataStoreVOList) {
 
-                // if this snapshot belongs to the storagePool that was passed 
in
-                if (snapshotDetails != null && snapshotDetails.getValue() != 
null && Long.parseLong(snapshotDetails.getValue()) == storagePool.getId()) {
-                    snapshotDetails = 
snapshotDetailsDao.findDetail(snapshot.getId(), SolidFireUtil.VOLUME_SIZE);
-
-                    if (snapshotDetails != null && snapshotDetails.getValue() 
!= null) {
-                        long snapshotSize = 
Long.parseLong(snapshotDetails.getValue());
+                usedSpace += snapshot.getPhysicalSize();
 
-                        usedSpace += snapshotSize;
-                    }
-                }
             }
         }
 
-        List<VMTemplateStoragePoolVO> lstTemplatePoolRefs = 
tmpltPoolDao.listByPoolId(storagePool.getId());
+        List<VMTemplateStoragePoolVO> vmTemplateStoragePoolVOList = 
vmTemplatePoolDao.listByPoolIdAndState(storagePool.getId(), 
ObjectInDataStoreStateMachine.State.Ready);
 
-        if (lstTemplatePoolRefs != null) {
-            for (VMTemplateStoragePoolVO templatePoolRef : 
lstTemplatePoolRefs) {
-                usedSpace += templatePoolRef.getTemplateSize();
+        if (vmTemplateStoragePoolVOList != null) {
+            for (VMTemplateStoragePoolVO template : 
vmTemplateStoragePoolVOList) {
+                usedSpace += template.getTemplateSize();
             }
         }
 
@@ -487,7 +455,7 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
      */
     @Override
     public long getBytesRequiredForTemplate(TemplateInfo templateInfo, 
StoragePool storagePool) {
-        List<VMTemplateStoragePoolVO> lstTemplatePoolRefs = 
tmpltPoolDao.listByPoolId(storagePool.getId());
+        List<VMTemplateStoragePoolVO> lstTemplatePoolRefs = 
vmTemplatePoolDao.listByPoolId(storagePool.getId());
 
         if (lstTemplatePoolRefs != null) {
             for (VMTemplateStoragePoolVO templatePoolRef : 
lstTemplatePoolRefs) {
@@ -740,7 +708,7 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
             sfVolumeId = Long.parseLong(snapshotDetails.getValue());
         } else if (dataObjectType == DataObjectType.TEMPLATE) {
             // get the cached template on this storage
-            VMTemplateStoragePoolVO templatePoolRef = 
tmpltPoolDao.findByPoolTemplate(storagePoolId, dataObjectId);
+            VMTemplateStoragePoolVO templatePoolRef = 
vmTemplatePoolDao.findByPoolTemplate(storagePoolId, dataObjectId);
 
             if (templatePoolRef != null) {
                 sfVolumeId = 
Long.parseLong(templatePoolRef.getLocalDownloadPath());
@@ -1166,13 +1134,13 @@ public class SolidFirePrimaryDataStoreDriver implements 
PrimaryDataStoreDriver {
 
         String iqn = sfVolume.getIqn();
 
-        VMTemplateStoragePoolVO templatePoolRef = 
tmpltPoolDao.findByPoolTemplate(storagePoolId, templateInfo.getId());
+        VMTemplateStoragePoolVO templatePoolRef = 
vmTemplatePoolDao.findByPoolTemplate(storagePoolId, templateInfo.getId());
 
         templatePoolRef.setInstallPath(iqn);
         templatePoolRef.setLocalDownloadPath(Long.toString(sfVolume.getId()));
         templatePoolRef.setTemplateSize(sfVolume.getTotalSize());
 
-        tmpltPoolDao.update(templatePoolRef.getId(), templatePoolRef);
+        vmTemplatePoolDao.update(templatePoolRef.getId(), templatePoolRef);
 
         StoragePoolVO storagePool = storagePoolDao.findById(storagePoolId);
 

Reply via email to