fix creating snapshot

This commit is contained in:
Edison Su 2013-05-06 18:26:33 -07:00
parent 2d544e7127
commit 9f7bad2cef
14 changed files with 434 additions and 53 deletions

View File

@ -65,6 +65,7 @@ public class DownloadCommand extends AbstractDownloadCommand implements Internal
}
public DownloadCommand(TemplateObjectTO template, Long maxDownloadSizeInBytes) {
super(template.getName(), template.getOrigUrl(), template.getFormat(), template.getAccountId());
this._store = template.getDataStore();
this.installPath = template.getPath();

View File

@ -370,7 +370,7 @@ public class AncientDataMotionStrategy implements DataMotionStrategy {
DataObject cacheData = null;
try {
if (destData.getDataStore().getRole() != DataStoreRole.ImageCache) {
if (needCacheStorage(srcData, destData)) {
cacheData = cacheMgr.getCacheObject(srcData, destData.getDataStore().getScope());
CopyCommand cmd = new CopyCommand(srcData.getTO(), destData.getTO(), _backupsnapshotwait);

View File

@ -18,6 +18,356 @@
*/
package org.apache.cloudstack.storage.test;
public class SnapshotTest {
import java.net.URI;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
import java.util.concurrent.ExecutionException;
import javax.inject.Inject;
import org.apache.cloudstack.engine.subsystem.api.storage.DataObject;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStore;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreManager;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreProviderManager;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPointSelector;
import org.apache.cloudstack.engine.subsystem.api.storage.SnapshotDataFactory;
import org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.SnapshotService;
import org.apache.cloudstack.engine.subsystem.api.storage.SnapshotStrategy;
import org.apache.cloudstack.engine.subsystem.api.storage.TemplateDataFactory;
import org.apache.cloudstack.engine.subsystem.api.storage.TemplateInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.TemplateService;
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.VolumeService;
import org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine.Event;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeService.VolumeApiResult;
import org.apache.cloudstack.engine.subsystem.api.storage.type.RootDisk;
import org.apache.cloudstack.framework.async.AsyncCallFuture;
import org.apache.cloudstack.storage.RemoteHostEndPoint;
import org.apache.cloudstack.storage.command.CopyCmdAnswer;
import org.apache.cloudstack.storage.datastore.db.ImageStoreDao;
import org.apache.cloudstack.storage.datastore.db.ImageStoreVO;
import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
import org.apache.cloudstack.storage.datastore.db.StoragePoolVO;
import org.apache.cloudstack.storage.datastore.db.TemplateDataStoreDao;
import org.apache.cloudstack.storage.to.TemplateObjectTO;
import org.apache.cloudstack.storage.volume.db.VolumeDao2;
import org.apache.cloudstack.storage.volume.db.VolumeVO;
import org.mockito.Mockito;
import org.springframework.test.context.ContextConfiguration;
import org.testng.AssertJUnit;
import org.testng.annotations.Test;
import com.cloud.agent.AgentManager;
import com.cloud.dc.ClusterVO;
import com.cloud.dc.DataCenterVO;
import com.cloud.dc.HostPodVO;
import com.cloud.dc.DataCenter.NetworkType;
import com.cloud.dc.dao.ClusterDao;
import com.cloud.dc.dao.DataCenterDao;
import com.cloud.dc.dao.HostPodDao;
import com.cloud.host.Host;
import com.cloud.host.HostVO;
import com.cloud.host.Host.Type;
import com.cloud.host.dao.HostDao;
import com.cloud.hypervisor.Hypervisor.HypervisorType;
import com.cloud.org.Cluster.ClusterType;
import com.cloud.org.Managed.ManagedState;
import com.cloud.resource.ResourceManager;
import com.cloud.resource.ResourceState;
import com.cloud.storage.DataStoreRole;
import com.cloud.storage.ScopeType;
import com.cloud.storage.Snapshot;
import com.cloud.storage.SnapshotVO;
import com.cloud.storage.Storage;
import com.cloud.storage.StoragePoolStatus;
import com.cloud.storage.VMTemplateVO;
import com.cloud.storage.Storage.StoragePoolType;
import com.cloud.storage.Storage.TemplateType;
import com.cloud.storage.dao.SnapshotDao;
import com.cloud.storage.dao.VMTemplateDao;
import com.cloud.utils.component.ComponentContext;
@ContextConfiguration(locations={"classpath:/storageContext.xml"})
public class SnapshotTest extends CloudStackTestNGBase {
@Inject
ImageStoreDao imageStoreDao;
ImageStoreVO imageStore;
Long dcId;
Long clusterId;
Long podId;
HostVO host;
String primaryName = "my primary data store";
DataStore primaryStore;
@Inject
HostDao hostDao;
@Inject
TemplateService imageService;
@Inject
VolumeService volumeService;
@Inject
VMTemplateDao imageDataDao;
@Inject
VolumeDao2 volumeDao;
@Inject
HostPodDao podDao;
@Inject
ClusterDao clusterDao;
@Inject
DataCenterDao dcDao;
@Inject
PrimaryDataStoreDao primaryStoreDao;
@Inject
DataStoreProviderManager dataStoreProviderMgr;
@Inject
TemplateDataStoreDao templateStoreDao;
@Inject
TemplateDataFactory templateFactory;
@Inject
PrimaryDataStoreDao primaryDataStoreDao;
@Inject
AgentManager agentMgr;
@Inject
DataStoreManager dataStoreMgr;
@Inject
ResourceManager resourceMgr;
@Inject
VolumeDataFactory volFactory;
@Inject SnapshotDataFactory snapshotFactory;
@Inject
List<SnapshotStrategy> snapshotStrategies;
@Inject
SnapshotService snapshotSvr;
@Inject
SnapshotDao snapshotDao;
@Inject
EndPointSelector epSelector;
long primaryStoreId;
VMTemplateVO image;
String imageStoreName = "testImageStore";
@Test(priority = -1)
public void setUp() {
ComponentContext.initComponentsLifeCycle();
host = hostDao.findByGuid(this.getHostGuid());
if (host != null) {
dcId = host.getDataCenterId();
clusterId = host.getClusterId();
podId = host.getPodId();
imageStore = this.imageStoreDao.findByName(imageStoreName);
} else {
//create data center
DataCenterVO dc = new DataCenterVO(UUID.randomUUID().toString(), "test", "8.8.8.8", null, "10.0.0.1", null, "10.0.0.1/24",
null, null, NetworkType.Basic, null, null, true, true, null, null);
dc = dcDao.persist(dc);
dcId = dc.getId();
//create pod
HostPodVO pod = new HostPodVO(UUID.randomUUID().toString(), dc.getId(), this.getHostGateway(), this.getHostCidr(), 8, "test");
pod = podDao.persist(pod);
podId = pod.getId();
//create xen cluster
ClusterVO cluster = new ClusterVO(dc.getId(), pod.getId(), "devcloud cluster");
cluster.setHypervisorType(HypervisorType.XenServer.toString());
cluster.setClusterType(ClusterType.CloudManaged);
cluster.setManagedState(ManagedState.Managed);
cluster = clusterDao.persist(cluster);
clusterId = cluster.getId();
//create xen host
host = new HostVO(this.getHostGuid());
host.setName("devcloud xen host");
host.setType(Host.Type.Routing);
host.setPrivateIpAddress(this.getHostIp());
host.setDataCenterId(dc.getId());
host.setVersion("6.0.1");
host.setAvailable(true);
host.setSetup(true);
host.setPodId(podId);
host.setLastPinged(0);
host.setResourceState(ResourceState.Enabled);
host.setHypervisorType(HypervisorType.XenServer);
host.setClusterId(cluster.getId());
host = hostDao.persist(host);
imageStore = new ImageStoreVO();
imageStore.setName(imageStoreName);
imageStore.setDataCenterId(dcId);
imageStore.setProviderName("CloudStack ImageStore Provider");
imageStore.setRole(DataStoreRole.Image);
imageStore.setUrl(this.getSecondaryStorage());
imageStore.setUuid(UUID.randomUUID().toString());
imageStore.setProtocol("nfs");
imageStore = imageStoreDao.persist(imageStore);
}
image = new VMTemplateVO();
image.setTemplateType(TemplateType.USER);
image.setUrl(this.getTemplateUrl());
image.setUniqueName(UUID.randomUUID().toString());
image.setName(UUID.randomUUID().toString());
image.setPublicTemplate(true);
image.setFeatured(true);
image.setRequiresHvm(true);
image.setBits(64);
image.setFormat(Storage.ImageFormat.VHD);
image.setEnablePassword(true);
image.setEnableSshKey(true);
image.setGuestOSId(1);
image.setBootable(true);
image.setPrepopulate(true);
image.setCrossZones(true);
image.setExtractable(true);
image = imageDataDao.persist(image);
/*TemplateDataStoreVO templateStore = new TemplateDataStoreVO();
templateStore.setDataStoreId(imageStore.getId());
templateStore.setDownloadPercent(100);
templateStore.setDownloadState(Status.DOWNLOADED);
templateStore.setDownloadUrl(imageStore.getUrl());
templateStore.setInstallPath(this.getImageInstallPath());
templateStore.setTemplateId(image.getId());
templateStoreDao.persist(templateStore);*/
DataStore store = this.dataStoreMgr.getDataStore(imageStore.getId(), DataStoreRole.Image);
TemplateInfo template = templateFactory.getTemplate(image.getId());
DataObject templateOnStore = store.create(template);
TemplateObjectTO to = new TemplateObjectTO();
to.setPath(this.getImageInstallPath());
CopyCmdAnswer answer = new CopyCmdAnswer(to);
templateOnStore.processEvent(Event.CreateOnlyRequested);
templateOnStore.processEvent(Event.OperationSuccessed, answer);
}
@Override
protected void injectMockito() {
List<HostVO> hosts = new ArrayList<HostVO>();
hosts.add(this.host);
Mockito.when(resourceMgr.listAllUpAndEnabledHosts((Type) Mockito.any(), Mockito.anyLong(), Mockito.anyLong(), Mockito.anyLong())).thenReturn(hosts);
RemoteHostEndPoint ep = RemoteHostEndPoint.getHypervisorHostEndPoint(this.host.getId(), this.host.getPrivateIpAddress());
Mockito.when(epSelector.select(Mockito.any(DataObject.class), Mockito.any(DataObject.class))).thenReturn(ep);
Mockito.when(epSelector.select(Mockito.any(DataObject.class))).thenReturn(ep);
Mockito.when(epSelector.select(Mockito.any(DataStore.class))).thenReturn(ep);
}
public DataStore createPrimaryDataStore() {
try {
String uuid = UUID.nameUUIDFromBytes(this.getPrimaryStorageUrl().getBytes()).toString();
List<StoragePoolVO> pools = primaryDataStoreDao.findPoolByName(this.primaryName);
if (pools.size() > 0) {
return this.dataStoreMgr.getPrimaryDataStore(pools.get(0).getId());
}
/*DataStoreProvider provider = dataStoreProviderMgr.getDataStoreProvider("cloudstack primary data store provider");
Map<String, Object> params = new HashMap<String, Object>();
URI uri = new URI(this.getPrimaryStorageUrl());
params.put("url", this.getPrimaryStorageUrl());
params.put("server", uri.getHost());
params.put("path", uri.getPath());
params.put("protocol", Storage.StoragePoolType.NetworkFilesystem);
params.put("zoneId", dcId);
params.put("clusterId", clusterId);
params.put("name", this.primaryName);
params.put("port", 1);
params.put("podId", this.podId);
params.put("roles", DataStoreRole.Primary.toString());
params.put("uuid", uuid);
params.put("providerName", String.valueOf(provider.getName()));
DataStoreLifeCycle lifeCycle = provider.getDataStoreLifeCycle();
DataStore store = lifeCycle.initialize(params);
ClusterScope scope = new ClusterScope(clusterId, podId, dcId);
lifeCycle.attachCluster(store, scope);*/
StoragePoolVO pool = new StoragePoolVO();
pool.setClusterId(clusterId);
pool.setDataCenterId(dcId);
URI uri = new URI(this.getPrimaryStorageUrl());
pool.setHostAddress(uri.getHost());
pool.setPath(uri.getPath());
pool.setPort(0);
pool.setName(this.primaryName);
pool.setUuid(this.getPrimaryStorageUuid());
pool.setStatus(StoragePoolStatus.Up);
pool.setPoolType(StoragePoolType.NetworkFilesystem);
pool.setPodId(podId);
pool.setScope(ScopeType.CLUSTER);
pool.setStorageProviderName("cloudstack primary data store provider");
pool = this.primaryStoreDao.persist(pool);
DataStore store = this.dataStoreMgr.getPrimaryDataStore(pool.getId());
return store;
} catch (Exception e) {
return null;
}
}
private SnapshotVO createSnapshotInDb(VolumeInfo volume) {
Snapshot.Type snapshotType = Snapshot.Type.MANUAL;
SnapshotVO snapshotVO = new SnapshotVO(volume.getDataCenterId(), 2, 1, volume.getId(), 1L, UUID.randomUUID().toString(),
(short) snapshotType.ordinal(), snapshotType.name(), volume.getSize(), HypervisorType.XenServer);
return this.snapshotDao.persist(snapshotVO);
}
private VolumeVO createVolume(Long templateId, long dataStoreId) {
VolumeVO volume = new VolumeVO(1000, new RootDisk().toString(), UUID.randomUUID().toString(), templateId);
volume.setDataCenterId(this.dcId);
volume.setPoolId(dataStoreId);
volume = volumeDao.persist(volume);
return volume;
}
public VolumeInfo createCopyBaseImage() {
DataStore primaryStore = createPrimaryDataStore();
primaryStoreId = primaryStore.getId();
primaryStore = this.dataStoreMgr.getPrimaryDataStore(primaryStoreId);
VolumeVO volume = createVolume(image.getId(), primaryStore.getId());
VolumeInfo volInfo = this.volFactory.getVolume(volume.getId());
AsyncCallFuture<VolumeApiResult> future = this.volumeService.createVolumeFromTemplateAsync(volInfo, this.primaryStoreId, this.templateFactory.getTemplate(this.image.getId()));
VolumeApiResult result;
try {
result = future.get();
return result.getVolume();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (ExecutionException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
@Test
public void createSnapshot() {
VolumeInfo vol = createCopyBaseImage();
SnapshotVO snapshotVO = createSnapshotInDb(vol);
SnapshotInfo snapshot = this.snapshotFactory.getSnapshot(snapshotVO.getId(), vol.getDataStore());
for (SnapshotStrategy strategy : this.snapshotStrategies) {
if (strategy.canHandle(snapshot)) {
strategy.takeSnapshot(snapshot);
}
}
}
//@Test
public void testCreateDataDisk() {
DataStore primaryStore = createPrimaryDataStore();
primaryStoreId = primaryStore.getId();
primaryStore = this.dataStoreMgr.getPrimaryDataStore(primaryStoreId);
VolumeVO volume = createVolume(null, primaryStore.getId());
VolumeInfo volInfo = this.volFactory.getVolume(volume.getId());
this.volumeService.createVolumeAsync(volInfo, primaryStore);
}
}

View File

@ -42,6 +42,7 @@ import org.apache.cloudstack.framework.async.AsyncCallbackDispatcher;
import org.apache.cloudstack.framework.async.AsyncCompletionCallback;
import org.apache.cloudstack.framework.async.AsyncRpcConext;
import org.apache.cloudstack.storage.command.CommandResult;
import org.apache.cloudstack.storage.command.CopyCmdAnswer;
import org.apache.cloudstack.storage.datastore.ObjectInDataStoreManager;
import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
import org.apache.cloudstack.storage.datastore.db.SnapshotDataStoreDao;
@ -170,6 +171,7 @@ public class SnapshotServiceImpl implements SnapshotService {
try {
snapshot.processEvent(Event.OperationSuccessed, result.getAnswer());
snapshot.processEvent(Snapshot.Event.OperationSucceeded);
} catch (Exception e) {
s_logger.debug("Failed to create snapshot: ", e);
snapResult.setResult(e.toString());
@ -323,12 +325,8 @@ public class SnapshotServiceImpl implements SnapshotService {
}
try {
BackupSnapshotAnswer answer = (BackupSnapshotAnswer)result.getAnswer();
DataObjectInStore dataInStore = objInStoreMgr.findObject(destSnapshot, destSnapshot.getDataStore());
dataInStore.setInstallPath(answer.getBackupSnapshotName());
objInStoreMgr.update(destSnapshot, Event.OperationSuccessed);
CopyCmdAnswer answer = (CopyCmdAnswer)result.getAnswer();
destSnapshot.processEvent(Event.OperationSuccessed, result.getAnswer());
srcSnapshot.processEvent(Snapshot.Event.OperationSucceeded);
snapResult = new SnapshotResult(this.snapshotfactory.getSnapshot(destSnapshot.getId(), destSnapshot.getDataStore()), answer);
future.complete(snapResult);

View File

@ -56,7 +56,7 @@ public class XenserverSnapshotStrategy extends SnapshotStrategyBase {
@Override
public SnapshotInfo backupSnapshot(SnapshotInfo snapshot) {
SnapshotInfo parentSnapshot = snapshot.getParent();
if (parentSnapshot.getPath().equalsIgnoreCase(snapshot.getPath())) {
if (parentSnapshot != null && parentSnapshot.getPath().equalsIgnoreCase(snapshot.getPath())) {
s_logger.debug("backup an empty snapshot");
//don't need to backup this snapshot
SnapshotDataStoreVO parentSnapshotOnBackupStore = this.snapshotStoreDao.findBySnapshot(parentSnapshot.getId(), DataStoreRole.Image);

View File

@ -63,19 +63,31 @@ public class LocalHostEndpoint implements EndPoint {
private class CmdRunner2 implements Runnable {
final Command cmd;
final AsyncCompletionCallback<DownloadAnswer> callback;
public CmdRunner2(Command cmd, AsyncCompletionCallback<DownloadAnswer> callback) {
final Listener listener;
public CmdRunner2(Command cmd, Listener listener) {
this.cmd = cmd;
this.callback = callback;
this.listener = listener;
}
@Override
public void run() {
try {
DownloadAnswer answer = (DownloadAnswer) sendMessage(cmd);
callback.complete(answer);
Answer[] answers = new Answer[1];
answers[0] = answer;
listener.processAnswers(getId(), 0, answers);
if (listener instanceof DownloadListener) {
DownloadListener dwldListener = (DownloadListener)listener;
dwldListener.getCallback().complete(answer);
}
} catch (Exception ex) {
DownloadAnswer fail = new DownloadAnswer("Error in handling DownloadCommand : " + ex.getMessage(), VMTemplateStorageResourceAssoc.Status.DOWNLOAD_ERROR);
callback.complete(fail);
Answer[] answers = new Answer[1];
answers[0] = fail;
listener.processAnswers(getId(), 0, answers);
if (listener instanceof DownloadListener) {
DownloadListener dwldListener = (DownloadListener)listener;
dwldListener.getCallback().complete(fail);
}
}
}
}
@ -89,7 +101,7 @@ public class LocalHostEndpoint implements EndPoint {
public void sendMessageAsyncWithListener(Command cmd, Listener listner) {
if (listner instanceof DownloadListener) {
DownloadListener listener = (DownloadListener)listner;
executor.schedule(new CmdRunner2(cmd, listener.getCallback()), 10, TimeUnit.SECONDS);
executor.schedule(new CmdRunner2(cmd, listener), 10, TimeUnit.SECONDS);
}
}
public ServerResource getResource() {

View File

@ -227,6 +227,8 @@ public class ObjectInDataStoreManagerImpl implements ObjectInDataStoreManager {
this.stateMachines.transitTo(obj, event, null,
templatePoolDao);
} else if (data.getType() == DataObjectType.SNAPSHOT && data.getDataStore().getRole() == DataStoreRole.Primary) {
this.stateMachines.transitTo(obj, event, null, snapshotDataStoreDao);
} else {
throw new CloudRuntimeException("Invalid data or store type: " + data.getType() + " " + data.getDataStore().getRole());
}
@ -270,6 +272,8 @@ public class ObjectInDataStoreManagerImpl implements ObjectInDataStoreManager {
}
} else if (type == DataObjectType.TEMPLATE && role == DataStoreRole.Primary) {
vo = templatePoolDao.findByPoolTemplate(dataStoreId, objId);
} else if (type == DataObjectType.SNAPSHOT && role == DataStoreRole.Primary) {
vo = snapshotDataStoreDao.findByStoreSnapshot(role, dataStoreId, objId);
} else {
s_logger.debug("Invalid data or store type: " + type + " " + role);
throw new CloudRuntimeException("Invalid data or store type: " + type + " " + role);

View File

@ -380,6 +380,7 @@ public class VolumeObject implements VolumeInfo {
VolumeObjectTO newVol = (VolumeObjectTO)cpyAnswer.getNewData();
vol.setPath(newVol.getPath());
vol.setSize(newVol.getSize());
vol.setPoolId(this.getDataStore().getId());
volumeDao.update(vol.getId(), vol);
} else if (answer instanceof CreateObjectAnswer) {
CreateObjectAnswer createAnswer =(CreateObjectAnswer)answer;
@ -387,6 +388,7 @@ public class VolumeObject implements VolumeInfo {
VolumeVO vol = this.volumeDao.findById(this.getId());
vol.setPath(newVol.getPath());
vol.setSize(newVol.getSize());
vol.setPoolId(this.getDataStore().getId());
volumeDao.update(vol.getId(), vol);
}
} else if (this.dataStore.getRole() == DataStoreRole.Image) {

View File

@ -358,17 +358,28 @@ public class VolumeServiceImpl implements VolumeService {
templateOnPrimaryStoreObj.processEvent(Event.CreateOnlyRequested);
} catch (Exception e) {
try {
templateOnPrimaryStoreObj = waitForTemplateDownloaded(dataStore, template);
} finally {
if (templateOnPrimaryStoreObj == null) {
VolumeApiResult result = new VolumeApiResult(volume);
result.setResult(e.toString());
caller.complete(result);
return;
}
templateOnPrimaryStoreObj = waitForTemplateDownloaded(dataStore, template);
} catch(Exception e1) {
s_logger.debug("wait for template:" + template.getId() + " downloading finished, but failed");
VolumeApiResult result = new VolumeApiResult(volume);
result.setResult(e1.toString());
caller.complete(result);
return;
}
if (templateOnPrimaryStoreObj == null) {
VolumeApiResult result = new VolumeApiResult(volume);
result.setResult("wait for template:" + template.getId() + " downloading finished, but failed");
caller.complete(result);
return;
} else {
s_logger.debug("waiting for template:" + template.getId() + " downloading finished, success");
VolumeApiResult result = new VolumeApiResult(volume);
future.complete(result);
return;
}
}
try {
motionSrv.copyAsync(template, templateOnPrimaryStoreObj, caller);
} catch (Exception e) {

View File

@ -170,35 +170,35 @@ public class XenServerStorageResource {
String snapshotUUID = null;
try {
String volumeUUID = snapshotTO.getVolume().getPath();
VDI volume = VDI.getByUuid(conn, volumeUUID);
String volumeUUID = snapshotTO.getVolume().getPath();
VDI volume = VDI.getByUuid(conn, volumeUUID);
VDI snapshot = volume.snapshot(conn, new HashMap<String, String>());
VDI snapshot = volume.snapshot(conn, new HashMap<String, String>());
if (snapshotName != null) {
snapshot.setNameLabel(conn, snapshotName);
if (snapshotName != null) {
snapshot.setNameLabel(conn, snapshotName);
}
snapshotUUID = snapshot.getUuid(conn);
String preSnapshotUUID = snapshotTO.getParentSnapshotPath();
//check if it is a empty snapshot
if( preSnapshotUUID != null) {
SR sr = volume.getSR(conn);
String srUUID = sr.getUuid(conn);
String type = sr.getType(conn);
Boolean isISCSI = IsISCSI(type);
String snapshotParentUUID = getVhdParent(conn, srUUID, snapshotUUID, isISCSI);
String preSnapshotParentUUID = getVhdParent(conn, srUUID, preSnapshotUUID, isISCSI);
if( snapshotParentUUID != null && snapshotParentUUID.equals(preSnapshotParentUUID)) {
// this is empty snapshot, remove it
snapshot.destroy(conn);
snapshotUUID = preSnapshotUUID;
}
snapshotUUID = snapshot.getUuid(conn);
String preSnapshotUUID = snapshotTO.getPath();
//check if it is a empty snapshot
if( preSnapshotUUID != null) {
SR sr = volume.getSR(conn);
String srUUID = sr.getUuid(conn);
String type = sr.getType(conn);
Boolean isISCSI = IsISCSI(type);
String snapshotParentUUID = getVhdParent(conn, srUUID, snapshotUUID, isISCSI);
String preSnapshotParentUUID = getVhdParent(conn, srUUID, preSnapshotUUID, isISCSI);
if( snapshotParentUUID != null && snapshotParentUUID.equals(preSnapshotParentUUID)) {
// this is empty snapshot, remove it
snapshot.destroy(conn);
snapshotUUID = preSnapshotUUID;
}
}
SnapshotObjectTO newSnapshot = new SnapshotObjectTO();
newSnapshot.setPath(snapshotUUID);
return new CreateObjectAnswer(newSnapshot);
}
SnapshotObjectTO newSnapshot = new SnapshotObjectTO();
newSnapshot.setPath(snapshotUUID);
return new CreateObjectAnswer(newSnapshot);
} catch (XenAPIException e) {
details += ", reason: " + e.toString();
s_logger.warn(details, e);

View File

@ -190,7 +190,8 @@ public class CloudStackPrimaryDataStoreDriverImpl implements PrimaryDataStoreDri
DataTO snapshotTO = snapshot.getTO();
CreateObjectCommand cmd = new CreateObjectCommand(snapshotTO);
Answer answer = storageMgr.sendToPool((StoragePool)snapshot.getDataStore(), null, cmd);
EndPoint ep = this.epSelecotor.select(snapshot);
Answer answer = ep.sendMessage(cmd);
result = new CreateCmdResult(null, answer);
if (answer != null && !answer.getResult()) {
@ -198,6 +199,7 @@ public class CloudStackPrimaryDataStoreDriverImpl implements PrimaryDataStoreDri
}
callback.complete(result);
return;
} catch (Exception e) {
s_logger.debug("Failed to take snapshot: " + snapshot.getId(), e);
result = new CreateCmdResult(null, null);

View File

@ -105,14 +105,14 @@ public class SamplePrimaryDataStoreDriverImpl implements PrimaryDataStoreDriver
@Override
public void deleteAsync(DataObject vo, AsyncCompletionCallback<CommandResult> callback) {
DeleteCommand cmd = new DeleteCommand(vo.getUri());
/*DeleteCommand cmd = new DeleteCommand(vo.getUri());
EndPoint ep = selector.select(vo);
AsyncRpcConext<CommandResult> context = new AsyncRpcConext<CommandResult>(callback);
AsyncCallbackDispatcher<SamplePrimaryDataStoreDriverImpl, Answer> caller = AsyncCallbackDispatcher.create(this);
caller.setCallback(caller.getTarget().deleteCallback(null, null))
.setContext(context);
ep.sendMessageAsync(cmd, caller);
ep.sendMessageAsync(cmd, caller);*/
}
public Void deleteCallback(AsyncCallbackDispatcher<SamplePrimaryDataStoreDriverImpl, Answer> callback, AsyncRpcConext<CommandResult> context) {

View File

@ -2487,6 +2487,7 @@ public class VolumeManagerImpl extends ManagerBase implements VolumeManager {
payload.setSnapshotId(snapshotId);
payload.setSnapshotPolicyId(policyId);
payload.setAccount(account);
volume.addPayload(payload);
return this.volService.takeSnapshot(volume);
}

View File

@ -170,7 +170,7 @@ CREATE TABLE `cloud`.`snapshot_store_ref` (
`parent_snapshot_id` bigint unsigned DEFAULT 0,
`install_path` varchar(255),
`state` varchar(255) NOT NULL,
`destroyed` tinyint(1) COMMENT 'indicates whether the snapshot_store entry was destroyed by the user or not',
`removed` datetime COMMENT 'date removed if not null',
`update_count` bigint unsigned,
`updated` datetime,
PRIMARY KEY (`id`),