From ffdf567b5843cc93ccb5c4e35ce765834da17099 Mon Sep 17 00:00:00 2001 From: Min Chen Date: Mon, 22 Apr 2013 13:19:04 -0700 Subject: [PATCH] Add implemention to pick EndPoint for secondary storage --- .../api/storage/TemplateService.java | 1 - .../endpoint/DefaultEndPointSelector.java | 50 +++++++++++++++---- .../vmware/manager/VmwareManagerImpl.java | 2 +- .../CloudStackImageStoreDriverImpl.java | 18 +++---- 4 files changed, 51 insertions(+), 20 deletions(-) diff --git a/engine/api/src/org/apache/cloudstack/engine/subsystem/api/storage/TemplateService.java b/engine/api/src/org/apache/cloudstack/engine/subsystem/api/storage/TemplateService.java index f04b14df050..dd017a11327 100644 --- a/engine/api/src/org/apache/cloudstack/engine/subsystem/api/storage/TemplateService.java +++ b/engine/api/src/org/apache/cloudstack/engine/subsystem/api/storage/TemplateService.java @@ -18,7 +18,6 @@ */ package org.apache.cloudstack.engine.subsystem.api.storage; -import org.apache.cloudstack.engine.subsystem.api.storage.VolumeService.VolumeApiResult; import org.apache.cloudstack.framework.async.AsyncCallFuture; import org.apache.cloudstack.framework.async.AsyncCompletionCallback; diff --git a/engine/storage/src/org/apache/cloudstack/storage/endpoint/DefaultEndPointSelector.java b/engine/storage/src/org/apache/cloudstack/storage/endpoint/DefaultEndPointSelector.java index bda2995952b..37ebccde8c8 100644 --- a/engine/storage/src/org/apache/cloudstack/storage/endpoint/DefaultEndPointSelector.java +++ b/engine/storage/src/org/apache/cloudstack/storage/endpoint/DefaultEndPointSelector.java @@ -22,6 +22,7 @@ import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.util.ArrayList; +import java.util.Collections; import java.util.List; import javax.inject.Inject; @@ -37,6 +38,7 @@ import org.apache.cloudstack.storage.LocalHostEndpoint; import org.apache.log4j.Logger; import org.springframework.stereotype.Component; +import com.cloud.host.Host; import com.cloud.host.HostVO; import com.cloud.host.Status; import com.cloud.host.dao.HostDao; @@ -71,7 +73,7 @@ public class DefaultEndPointSelector implements EndPointSelector { return false; } } - + protected boolean moveBetweenCacheAndImage(DataStore srcStore, DataStore destStore) { DataStoreRole srcRole = srcStore.getRole(); DataStoreRole destRole = destStore.getRole(); @@ -162,7 +164,7 @@ public class DefaultEndPointSelector implements EndPointSelector { } else if (moveBetweenCacheAndImage(srcStore, destStore)) { EndPoint ep = findEndPointForImageMove(srcStore, destStore); if (ep == null) { - //if there is no ssvm agent running, use mgt server + //if there is no ssvm agent running, use mgt server ep = new LocalHostEndpoint(); } return ep; @@ -170,11 +172,41 @@ public class DefaultEndPointSelector implements EndPointSelector { // TODO Auto-generated method stub return null; } - + protected EndPoint findEndpointForPrimaryStorage(DataStore store) { return findEndPointInScope(store.getScope(), findOneHostOnPrimaryStorage); } - + + + protected EndPoint findEndpointForImageStorage(DataStore store) { + Long dcId = null; + Scope storeScope = store.getScope(); + if (storeScope.getScopeType() == ScopeType.ZONE) { + dcId = storeScope.getScopeId(); + } + // find ssvm that can be used to download data to store. For zone-wide + // image store, use SSVM for that zone. For region-wide store, + // we can arbitrarily pick one ssvm to do that task + List ssAHosts = listUpAndConnectingSecondaryStorageVmHost(dcId); + if (ssAHosts == null || ssAHosts.isEmpty()) { + return new LocalHostEndpoint(); // use local host as endpoint in + // case of no ssvm existing + } + Collections.shuffle(ssAHosts); + HostVO host = ssAHosts.get(0); + return RemoteHostEndPoint.getHypervisorHostEndPoint(host.getId(), host.getPrivateIpAddress()); + } + + private List listUpAndConnectingSecondaryStorageVmHost(Long dcId) { + SearchCriteriaService sc = SearchCriteria2.create(HostVO.class); + if (dcId != null) { + sc.addAnd(sc.getEntity().getDataCenterId(), Op.EQ, dcId); + } + sc.addAnd(sc.getEntity().getStatus(), Op.IN, com.cloud.host.Status.Up, com.cloud.host.Status.Connecting); + sc.addAnd(sc.getEntity().getType(), Op.EQ, Host.Type.SecondaryStorageVM); + return sc.list(); + } + @Override public EndPoint select(DataObject object) { DataStore store = object.getDataStore(); @@ -182,14 +214,14 @@ public class DefaultEndPointSelector implements EndPointSelector { return findEndpointForPrimaryStorage(store); } else if (store.getRole() == DataStoreRole.Image) { //in case there is no ssvm, directly send down command hypervisor host - //TODO: add code to handle in case ssvm is there - return findEndpointForPrimaryStorage(store); + // otherwise, send to localhost for bootstrap system vm template download + return findEndpointForImageStorage(store); }else { throw new CloudRuntimeException("not implemented yet"); } - + } - + @Override public List selectAll(DataStore store) { List endPoints = new ArrayList(); @@ -206,7 +238,7 @@ public class DefaultEndPointSelector implements EndPointSelector { endPoints.add(RemoteHostEndPoint.getHypervisorHostEndPoint(host.getId(), host.getPrivateIpAddress())); } - + } else { throw new CloudRuntimeException("shouldn't use it for other scope"); } diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java index ba99da11996..4ae0d17ac67 100755 --- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java +++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareManagerImpl.java @@ -710,7 +710,7 @@ public class VmwareManagerImpl extends ManagerBase implements VmwareManager, Vmw } @DB - private void updateClusterNativeHAState(HostVO host, StartupCommand cmd) { + private void updateClusterNativeHAState(Host host, StartupCommand cmd) { ClusterVO cluster = _clusterDao.findById(host.getClusterId()); if(cluster.getClusterType() == ClusterType.ExternalManaged) { if(cmd instanceof StartupRoutingCommand) { diff --git a/plugins/storage/image/default/src/org/apache/cloudstack/storage/datastore/driver/CloudStackImageStoreDriverImpl.java b/plugins/storage/image/default/src/org/apache/cloudstack/storage/datastore/driver/CloudStackImageStoreDriverImpl.java index 049a0364e8e..46aae5601d3 100644 --- a/plugins/storage/image/default/src/org/apache/cloudstack/storage/datastore/driver/CloudStackImageStoreDriverImpl.java +++ b/plugins/storage/image/default/src/org/apache/cloudstack/storage/datastore/driver/CloudStackImageStoreDriverImpl.java @@ -164,17 +164,17 @@ public class CloudStackImageStoreDriverImpl implements ImageStoreDriver { super(callback); this.data = data; } - + } @Override public void createAsync(DataObject data, AsyncCompletionCallback callback) { createObjectContext context = new createObjectContext(callback, data); - AsyncCallbackDispatcher caller = + AsyncCallbackDispatcher caller = AsyncCallbackDispatcher.create(this); caller.setContext(context); caller.setCallback(this.createAsyncCallback(null, null)); - + if (data.getType() == DataObjectType.TEMPLATE) { TemplateObject tData = (TemplateObject)data; _downloadMonitor.downloadTemplateToStorage(tData, tData.getDataStore(), caller); @@ -185,8 +185,8 @@ public class CloudStackImageStoreDriverImpl implements ImageStoreDriver { payload.getChecksum(), ImageFormat.valueOf(payload.getFormat().toUpperCase()), caller); } } - - protected Void createAsyncCallback(AsyncCallbackDispatcher callback, + + protected Void createAsyncCallback(AsyncCallbackDispatcher callback, createObjectContext context) { DownloadAnswer answer = callback.getResult(); DataObject obj = context.data; @@ -203,9 +203,9 @@ public class CloudStackImageStoreDriverImpl implements ImageStoreDriver { updateBuilder.setSize(answer.getTemplateSize()); updateBuilder.setPhysicalSize(answer.getTemplatePhySicalSize()); _templateStoreDao.update(store.getId(), updateBuilder); - + AsyncCompletionCallback caller = context.getParentCallback(); - + if (answer.getDownloadStatus() == VMTemplateStorageResourceAssoc.Status.DOWNLOAD_ERROR || answer.getDownloadStatus() == VMTemplateStorageResourceAssoc.Status.ABANDONED || answer.getDownloadStatus() == VMTemplateStorageResourceAssoc.Status.UNKNOWN) { @@ -219,8 +219,8 @@ public class CloudStackImageStoreDriverImpl implements ImageStoreDriver { templateDaoBuilder.setChecksum(answer.getCheckSum()); templateDao.update(obj.getId(), templateDaoBuilder); } - - + + CreateCmdResult result = new CreateCmdResult(null, null); caller.complete(result); }