use of org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo in project cloudstack by apache.
the class VolumeServiceImpl method createVolumeFromSnapshotCallback.
protected Void createVolumeFromSnapshotCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback, CreateVolumeFromBaseImageContext<VolumeApiResult> context) {
CopyCommandResult result = callback.getResult();
VolumeInfo volume = (VolumeInfo) context.templateOnStore;
SnapshotInfo snapshot = context.snapshot;
VolumeApiResult apiResult = new VolumeApiResult(volume);
Event event = null;
if (result.isFailed()) {
apiResult.setResult(result.getResult());
event = Event.OperationFailed;
} else {
event = Event.OperationSuccessed;
}
try {
if (result.isSuccess()) {
volume.processEvent(event, result.getAnswer());
} else {
volume.processEvent(event);
}
_volumeDetailsDao.removeDetail(volume.getId(), SNAPSHOT_ID);
} catch (Exception e) {
s_logger.debug("create volume from snapshot failed", e);
apiResult.setResult(e.toString());
}
AsyncCallFuture<VolumeApiResult> future = context.future;
future.complete(apiResult);
return null;
}
use of org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo in project cloudstack by apache.
the class XenserverSnapshotStrategy method deleteSnapshot.
@Override
public boolean deleteSnapshot(Long snapshotId) {
SnapshotVO snapshotVO = snapshotDao.findById(snapshotId);
if (snapshotVO.getState() == Snapshot.State.Allocated) {
snapshotDao.remove(snapshotId);
return true;
}
if (snapshotVO.getState() == Snapshot.State.Destroyed) {
return true;
}
if (Snapshot.State.Error.equals(snapshotVO.getState())) {
List<SnapshotDataStoreVO> storeRefs = snapshotStoreDao.findBySnapshotId(snapshotId);
for (SnapshotDataStoreVO ref : storeRefs) {
snapshotStoreDao.expunge(ref.getId());
}
snapshotDao.remove(snapshotId);
return true;
}
if (snapshotVO.getState() == Snapshot.State.CreatedOnPrimary) {
s_logger.debug("delete snapshot on primary storage:");
snapshotVO.setState(Snapshot.State.Destroyed);
snapshotDao.update(snapshotId, snapshotVO);
return true;
}
if (!Snapshot.State.BackedUp.equals(snapshotVO.getState()) && !Snapshot.State.Error.equals(snapshotVO.getState())) {
throw new InvalidParameterValueException("Can't delete snapshotshot " + snapshotId + " due to it is in " + snapshotVO.getState() + " Status");
}
// first mark the snapshot as destroyed, so that ui can't see it, but we
// may not destroy the snapshot on the storage, as other snapshots may
// depend on it.
SnapshotInfo snapshotOnImage = snapshotDataFactory.getSnapshot(snapshotId, DataStoreRole.Image);
if (snapshotOnImage == null) {
s_logger.debug("Can't find snapshot on backup storage, delete it in db");
snapshotDao.remove(snapshotId);
return true;
}
SnapshotObject obj = (SnapshotObject) snapshotOnImage;
try {
obj.processEvent(Snapshot.Event.DestroyRequested);
} catch (NoTransitionException e) {
s_logger.debug("Failed to set the state to destroying: ", e);
return false;
}
try {
boolean result = deleteSnapshotChain(snapshotOnImage);
obj.processEvent(Snapshot.Event.OperationSucceeded);
if (result) {
//snapshot is deleted on backup storage, need to delete it on primary storage
SnapshotDataStoreVO snapshotOnPrimary = snapshotStoreDao.findBySnapshot(snapshotId, DataStoreRole.Primary);
if (snapshotOnPrimary != null) {
SnapshotInfo snapshotOnPrimaryInfo = snapshotDataFactory.getSnapshot(snapshotId, DataStoreRole.Primary);
long volumeId = snapshotOnPrimary.getVolumeId();
VolumeVO volumeVO = volumeDao.findById(volumeId);
if (((PrimaryDataStoreImpl) snapshotOnPrimaryInfo.getDataStore()).getPoolType() == StoragePoolType.RBD && volumeVO != null) {
snapshotSvr.deleteSnapshot(snapshotOnPrimaryInfo);
}
snapshotOnPrimary.setState(State.Destroyed);
snapshotStoreDao.update(snapshotOnPrimary.getId(), snapshotOnPrimary);
}
}
} catch (Exception e) {
s_logger.debug("Failed to delete snapshot: ", e);
try {
obj.processEvent(Snapshot.Event.OperationFailed);
} catch (NoTransitionException e1) {
s_logger.debug("Failed to change snapshot state: " + e.toString());
}
return false;
}
return true;
}
use of org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo in project cloudstack by apache.
the class XenserverSnapshotStrategy method takeSnapshot.
@Override
@DB
public SnapshotInfo takeSnapshot(SnapshotInfo snapshot) {
Object payload = snapshot.getPayload();
if (payload != null) {
CreateSnapshotPayload createSnapshotPayload = (CreateSnapshotPayload) payload;
if (createSnapshotPayload.getQuiescevm()) {
throw new InvalidParameterValueException("can't handle quiescevm equal true for volume snapshot");
}
}
SnapshotVO snapshotVO = snapshotDao.acquireInLockTable(snapshot.getId());
if (snapshotVO == null) {
throw new CloudRuntimeException("Failed to get lock on snapshot:" + snapshot.getId());
}
try {
VolumeInfo volumeInfo = snapshot.getBaseVolume();
volumeInfo.stateTransit(Volume.Event.SnapshotRequested);
SnapshotResult result = null;
try {
result = snapshotSvr.takeSnapshot(snapshot);
if (result.isFailed()) {
s_logger.debug("Failed to take snapshot: " + result.getResult());
throw new CloudRuntimeException(result.getResult());
}
} finally {
if (result != null && result.isSuccess()) {
volumeInfo.stateTransit(Volume.Event.OperationSucceeded);
} else {
volumeInfo.stateTransit(Volume.Event.OperationFailed);
}
}
snapshot = result.getSnapshot();
DataStore primaryStore = snapshot.getDataStore();
boolean backupFlag = Boolean.parseBoolean(configDao.getValue(Config.BackupSnapshotAfterTakingSnapshot.toString()));
SnapshotInfo backupedSnapshot;
if (backupFlag) {
backupedSnapshot = backupSnapshot(snapshot);
} else {
// Fake it to get the transitions to fire in the proper order
s_logger.debug("skipping backup of snapshot due to configuration " + Config.BackupSnapshotAfterTakingSnapshot.toString());
SnapshotObject snapObj = (SnapshotObject) snapshot;
try {
snapObj.processEvent(Snapshot.Event.OperationNotPerformed);
} catch (NoTransitionException e) {
s_logger.debug("Failed to change state: " + snapshot.getId() + ": " + e.toString());
throw new CloudRuntimeException(e.toString());
}
backupedSnapshot = snapshot;
}
try {
SnapshotInfo parent = snapshot.getParent();
if (backupedSnapshot != null && parent != null && primaryStore instanceof PrimaryDataStoreImpl) {
if (((PrimaryDataStoreImpl) primaryStore).getPoolType() != StoragePoolType.RBD) {
Long parentSnapshotId = parent.getId();
while (parentSnapshotId != null && parentSnapshotId != 0L) {
SnapshotDataStoreVO snapshotDataStoreVO = snapshotStoreDao.findByStoreSnapshot(primaryStore.getRole(), primaryStore.getId(), parentSnapshotId);
if (snapshotDataStoreVO != null) {
parentSnapshotId = snapshotDataStoreVO.getParentSnapshotId();
snapshotStoreDao.remove(snapshotDataStoreVO.getId());
} else {
parentSnapshotId = null;
}
}
}
SnapshotDataStoreVO snapshotDataStoreVO = snapshotStoreDao.findByStoreSnapshot(primaryStore.getRole(), primaryStore.getId(), snapshot.getId());
if (snapshotDataStoreVO != null) {
snapshotDataStoreVO.setParentSnapshotId(0L);
snapshotStoreDao.update(snapshotDataStoreVO.getId(), snapshotDataStoreVO);
}
}
} catch (Exception e) {
s_logger.debug("Failed to clean up snapshots on primary storage", e);
}
return backupedSnapshot;
} finally {
if (snapshotVO != null) {
snapshotDao.releaseFromLockTable(snapshot.getId());
}
}
}
use of org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo in project cloudstack by apache.
the class SnapshotTestWithFakeData method testConcurrentSnapshot.
@Test
public void testConcurrentSnapshot() throws URISyntaxException, InterruptedException, ExecutionException {
DataStore store = createDataStore();
final FakePrimaryDataStoreDriver dataStoreDriver = (FakePrimaryDataStoreDriver) store.getDriver();
dataStoreDriver.makeTakeSnapshotSucceed(true);
final VolumeInfo volumeInfo = createVolume(1L, store);
Assert.assertTrue(volumeInfo.getState() == Volume.State.Ready);
vol = volumeInfo;
// final SnapshotPolicyVO policyVO = createSnapshotPolicy(vol.getId());
ExecutorService pool = Executors.newFixedThreadPool(2);
boolean result = false;
List<Future<Boolean>> future = new ArrayList<Future<Boolean>>();
for (int i = 0; i < 12; i++) {
final int cnt = i;
Future<Boolean> task = pool.submit(new Callable<Boolean>() {
@Override
public Boolean call() throws Exception {
boolean r = true;
try {
SnapshotVO snapshotVO = createSnapshotInDb(vol.getId());
VolumeObject volumeObject = (VolumeObject) vol;
Account account = mock(Account.class);
when(account.getId()).thenReturn(1L);
CreateSnapshotPayload createSnapshotPayload = mock(CreateSnapshotPayload.class);
when(createSnapshotPayload.getAccount()).thenReturn(account);
when(createSnapshotPayload.getSnapshotId()).thenReturn(snapshotVO.getId());
when(createSnapshotPayload.getSnapshotPolicyId()).thenReturn(0L);
volumeObject.addPayload(createSnapshotPayload);
if (cnt > 8) {
mockStorageMotionStrategy.makeBackupSnapshotSucceed(false);
}
SnapshotInfo newSnapshot = volumeService.takeSnapshot(vol);
if (newSnapshot == null) {
r = false;
}
} catch (Exception e) {
r = false;
}
return r;
}
});
Assert.assertTrue(task.get());
}
}
use of org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo in project cloudstack by apache.
the class SnapshotTestWithFakeData method testTakeSnapshotWithFailed.
//@Test
public void testTakeSnapshotWithFailed() throws URISyntaxException {
SnapshotVO snapshotVO = createSnapshotInDb();
DataStore store = null;
try {
store = createDataStore();
FakePrimaryDataStoreDriver dataStoreDriver = (FakePrimaryDataStoreDriver) store.getDriver();
dataStoreDriver.makeTakeSnapshotSucceed(false);
SnapshotInfo snapshotInfo = snapshotDataFactory.getSnapshot(snapshotVO.getId(), store);
SnapshotResult result = snapshotService.takeSnapshot(snapshotInfo);
Assert.assertFalse(result.isSuccess());
SnapshotDataStoreVO storeRef = snapshotDataStoreDao.findByStoreSnapshot(store.getRole(), store.getId(), snapshotVO.getId());
Assert.assertTrue(storeRef == null);
} finally {
snapshotDao.expunge(snapshotVO.getId());
if (store != null) {
primaryDataStoreDao.remove(store.getId());
}
}
}
Aggregations