add image motion interface

This commit is contained in:
Edison Su 2012-11-15 17:52:30 -08:00
parent 7a3ffb47e6
commit 23a35db952
25 changed files with 298 additions and 68 deletions

View File

@ -23,5 +23,6 @@ import org.apache.cloudstack.engine.entity.api.CloudStackEntity;
import com.cloud.template.VirtualMachineTemplate;
public interface TemplateEntity extends CloudStackEntity, VirtualMachineTemplate {
public long getPhysicalSize();
public long getVirtualSize();
}

View File

@ -19,6 +19,8 @@
package org.apache.cloudstack.engine.subsystem.api.storage;
import java.util.List;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
import com.cloud.hypervisor.Hypervisor.HypervisorType;
@ -29,4 +31,5 @@ public interface PrimaryDataStoreInfo {
public boolean isVolumeDiskTypeSupported(VolumeDiskType diskType);
public long getCapacity();
public long getAvailableCapacity();
public List<EndPoint> getEndPoints();
}

View File

@ -0,0 +1,7 @@
package org.apache.cloudstack.engine.subsystem.api.storage.type;
public class BaseImage extends VolumeTypeBase {
public BaseImage() {
this.type = "BaseImage";
}
}

View File

@ -25,6 +25,7 @@ import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.cloud.entity.api.VolumeEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.DataObjectBackupStorageOperationState;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStore;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.StorageOrchestrator;
import org.apache.cloudstack.engine.subsystem.api.storage.StorageProvider;
import org.apache.cloudstack.engine.subsystem.api.storage.TemplateProfile;
@ -32,10 +33,15 @@ import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeProfile;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeStrategy;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
import org.apache.cloudstack.engine.subsystem.api.storage.type.BaseImage;
import org.apache.cloudstack.engine.subsystem.api.storage.type.VolumeType;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.datastore.manager.PrimaryDataStoreManager;
import org.apache.cloudstack.storage.image.ImageManager;
import org.apache.cloudstack.storage.image.ImageService;
import org.apache.cloudstack.storage.image.TemplateEntityImpl;
import org.apache.cloudstack.storage.image.TemplateInfo;
import org.apache.cloudstack.storage.image.motion.ImageMotionService;
import org.apache.cloudstack.storage.manager.BackupStorageManager;
import org.apache.cloudstack.storage.manager.SecondaryStorageManager;
import org.apache.cloudstack.storage.volume.VolumeEntityImpl;
@ -92,6 +98,10 @@ public class StorageOrchestratorImpl implements StorageOrchestrator {
@Inject
VolumeService volumeService;
@Inject
ImageMotionService imageMotionService;
@Inject
ImageService imageService;
@Inject
PrimaryDataStoreManager primaryStorageMgr;
@DB
@ -343,12 +353,28 @@ public class StorageOrchestratorImpl implements StorageOrchestrator {
return volumeService.allocateVolumeInDb(size, type, volName, templateId);
}
protected VolumeInfo getVolumeInfo(VolumeEntity volume) {
VolumeEntityImpl vei = (VolumeEntityImpl)volume;
return vei.getVolumeInfo();
}
@Override
public boolean createVolumeFromTemplate(VolumeEntity volume, long dataStoreId, VolumeDiskType diskType, TemplateEntity template) {
PrimaryDataStore pd = primaryStorageMgr.getPrimaryDataStore(dataStoreId);
boolean existsOnPrimaryStorage = pd.templateExists(template.getId());
if (!existsOnPrimaryStorage) {
//pd.installTemplate(template);
TemplateInfo ti = ((TemplateEntityImpl)template).getTemplateInfo();
//TODO: hold lock
VolumeEntity baseImage = volumeService.allocateVolumeInDb(template.getVirtualSize(), new BaseImage(), "BaseImage-" + template.getName(), template.getId());
VolumeInfo vi = pd.createVolume(getVolumeInfo(baseImage), pd.getDefaultDiskType());
volumeService.startCopying(vi);
boolean copyResult = imageMotionService.copyTemplate(ti, vi);
if (copyResult) {
volumeService.copyingSucceed(vi);
} else {
volumeService.copyingFailed(vi);
}
}
return false;
}

View File

@ -0,0 +1,29 @@
package org.apache.cloudstack.storage.command;
import org.apache.cloudstack.storage.to.TemplateTO;
import org.apache.cloudstack.storage.to.VolumeTO;
import com.cloud.agent.api.Command;
public class CopyTemplateToPrimaryStorage extends Command {
private VolumeTO volume;
private TemplateTO template;
protected CopyTemplateToPrimaryStorage() {
super();
}
public CopyTemplateToPrimaryStorage(TemplateTO template, VolumeTO volume) {
super();
this.volume = volume;
this.template = template;
}
@Override
public boolean executeInSequence() {
// TODO Auto-generated method stub
return false;
}
}

View File

@ -0,0 +1,7 @@
package org.apache.cloudstack.storage.command;
import com.cloud.agent.api.Answer;
public class CopyTemplateToPrimaryStorageAnswer extends Answer {
}

View File

@ -18,13 +18,13 @@
*/
package org.apache.cloudstack.storage.command;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.to.VolumeTO;
import com.cloud.agent.api.Command;
public class CreateVolumeCommand extends Command {
protected VolumeInfo volumeInfo;
public CreateVolumeCommand(VolumeInfo volumeInfo) {
protected VolumeTO volumeInfo;
public CreateVolumeCommand(VolumeTO volumeInfo) {
super();
this.volumeInfo = volumeInfo;
}

View File

@ -14,6 +14,7 @@ import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskTyp
import org.apache.cloudstack.storage.HypervisorHostEndPoint;
import org.apache.cloudstack.storage.datastore.db.DataStoreVO;
import org.apache.cloudstack.storage.datastore.driver.PrimaryDataStoreDriver;
import org.apache.cloudstack.storage.image.TemplateInfo;
import org.apache.cloudstack.storage.image.TemplateObject;
import org.apache.cloudstack.storage.volume.VolumeEntityImpl;
@ -120,11 +121,11 @@ public class DefaultPrimaryDataStoreImpl implements PrimaryDataStore {
}
@Override
public VolumeObject createVolume(VolumeObject vo, VolumeDiskType diskType) {
public VolumeObject createVolume(VolumeInfo vi, VolumeDiskType diskType) {
if (!pdsInfo.isVolumeDiskTypeSupported(diskType)) {
return null;
}
VolumeObject vo = (VolumeObject)vi;
vo.setVolumeDiskType(diskType);
this.driver.createVolume(vo);
return vo;
@ -143,8 +144,15 @@ public class DefaultPrimaryDataStoreImpl implements PrimaryDataStore {
}
@Override
public boolean installTemplate(TemplateObject template) {
// TODO Auto-generated method stub
public boolean installTemplate(TemplateInfo template) {
return false;
}
@Override
public VolumeDiskType getDefaultDiskType() {
// TODO Auto-generated method stub
return null;
}
}

View File

@ -25,6 +25,7 @@ import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
import org.apache.cloudstack.storage.image.TemplateInfo;
import org.apache.cloudstack.storage.image.TemplateObject;
import org.apache.cloudstack.storage.volume.VolumeObject;
@ -33,10 +34,11 @@ public interface PrimaryDataStore extends PrimaryDataStoreInfo {
VolumeInfo getVolume(long id);
List<VolumeInfo> getVolumes();
boolean deleteVolume(long id);
VolumeObject createVolume(VolumeObject vo, VolumeDiskType diskType);
VolumeInfo createVolume(VolumeInfo vo, VolumeDiskType diskType);
List<EndPoint> getEndPoints();
PrimaryDataStoreInfo getDataStoreInfo();
boolean exists(VolumeInfo vi);
boolean templateExists(long templateId);
boolean installTemplate(TemplateObject template);
boolean installTemplate(TemplateInfo template);
VolumeDiskType getDefaultDiskType();
}

View File

@ -20,6 +20,7 @@ package org.apache.cloudstack.storage.datastore;
import java.util.List;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
@ -65,4 +66,10 @@ public class PrimaryDataStoreInfoImpl implements PrimaryDataStoreInfo {
public long getAvailableCapacity() {
return this.avail;
}
@Override
public List<EndPoint> getEndPoints() {
// TODO Auto-generated method stub
return null;
}
}

View File

@ -7,6 +7,7 @@ import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.command.CreateVolumeAnswer;
import org.apache.cloudstack.storage.command.CreateVolumeCommand;
import org.apache.cloudstack.storage.to.VolumeTO;
import org.apache.cloudstack.storage.volume.VolumeObject;
import org.apache.log4j.Logger;
import org.springframework.stereotype.Component;
@ -23,7 +24,7 @@ public class DefaultPrimaryDataStoreDriverImpl implements
List<EndPoint> endPoints = vol.getDataStore().getEndPoints();
int retries = 3;
VolumeInfo volInfo = vol;
CreateVolumeCommand createCmd = new CreateVolumeCommand(volInfo);
CreateVolumeCommand createCmd = new CreateVolumeCommand(new VolumeTO(volInfo));
Answer answer = null;
int i = 0;
boolean result = false;

View File

@ -16,16 +16,18 @@
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.cloudstack.engine.subsystem.api.storage;
package org.apache.cloudstack.storage.image;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
public interface ImageService {
boolean registerTemplate(long templateId, long imageStoreId);
boolean deleteTemplate(long templateId);
long registerIso(String isoUrl, long accountId);
boolean deleteIso(long isoId);
String grantTemplateAccess(long templateId, long endpointId);
String grantTemplateAccess(TemplateInfo template, EndPoint endpointId);
boolean revokeTemplateAccess(long templateId, long endpointId);
String grantIsoAccess(long isoId, long endpointId);
boolean revokeIsoAccess(long isoId, long endpointId);

View File

@ -21,7 +21,7 @@ package org.apache.cloudstack.storage.image;
import javax.inject.Inject;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.ImageService;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.storage.image.downloader.ImageDownloader;
import org.apache.cloudstack.storage.image.manager.ImageDataStoreManager;
import org.apache.cloudstack.storage.image.provider.ImageDataStoreProviderManager;
@ -62,12 +62,6 @@ public class ImageServiceImpl implements ImageService {
return false;
}
@Override
public String grantTemplateAccess(long templateId, long endpointId) {
ImageDataStore ids = imageStoreProviderMgr.getDataStoreFromTemplateId(templateId);
return ids.grantAccess(templateId, endpointId);
}
@Override
public boolean revokeTemplateAccess(long templateId, long endpointId) {
// TODO Auto-generated method stub
@ -91,4 +85,10 @@ public class ImageServiceImpl implements ImageService {
TemplateObject to = imageStoreProviderMgr.getTemplate(templateId);
return new TemplateEntityImpl(to);
}
@Override
public String grantTemplateAccess(TemplateInfo template, EndPoint endpointId) {
// TODO Auto-generated method stub
return null;
}
}

View File

@ -47,6 +47,10 @@ public class TemplateEntityImpl implements TemplateEntity {
return getImageDataStore().getImageDataStoreId();
}
public TemplateInfo getTemplateInfo() {
return this.templateInfo;
}
@Override
public String getUuid() {
// TODO Auto-generated method stub
@ -275,4 +279,16 @@ public class TemplateEntityImpl implements TemplateEntity {
return 0;
}
@Override
public long getPhysicalSize() {
// TODO Auto-generated method stub
return 0;
}
@Override
public long getVirtualSize() {
// TODO Auto-generated method stub
return 0;
}
}

View File

@ -0,0 +1,56 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.cloudstack.storage.image.motion;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.command.CopyTemplateToPrimaryStorage;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.image.TemplateInfo;
import org.apache.cloudstack.storage.to.TemplateTO;
import org.apache.cloudstack.storage.to.VolumeTO;
public class DefaultImageMotionStrategy implements ImageMotionStrategy {
@Override
public boolean canHandle(TemplateInfo template, VolumeInfo volume) {
// TODO Auto-generated method stub
return true;
}
//For default strategy, we will use one of endpoint in volume's datastore
@Override
public EndPoint getEndPoint(TemplateInfo template, VolumeInfo volume) {
PrimaryDataStoreInfo pdi = volume.getDataStore();
return pdi.getEndPoints().get(0);
}
@Override
public boolean copyTemplate(TemplateInfo template, VolumeInfo volume,
EndPoint ep) {
VolumeTO vt = new VolumeTO(volume);
TemplateTO tt = new TemplateTO(template);
CopyTemplateToPrimaryStorage copyCommand = new CopyTemplateToPrimaryStorage(tt, vt);
ep.sendMessage(copyCommand);
return true;
}
}

View File

@ -1,26 +0,0 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.cloudstack.storage.image.motion;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
public interface ImageMotionProvider {
public boolean canHandle(TemplateEntity template, PrimaryDataStore dataStoe);
}

View File

@ -19,9 +19,12 @@
package org.apache.cloudstack.storage.image.motion;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.image.TemplateInfo;
public interface ImageMotionService {
boolean copyTemplate(TemplateEntity template, PrimaryDataStoreInfo dataStore);
boolean copyTemplate(TemplateInfo template, VolumeInfo baseImage);
boolean copyIso(String isoUri, String destIsoUri);
}

View File

@ -18,11 +18,28 @@
*/
package org.apache.cloudstack.storage.image.motion;
import java.util.List;
import javax.inject.Inject;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.image.ImageService;
import org.apache.cloudstack.storage.image.TemplateInfo;
import org.apache.cloudstack.storage.volume.VolumeService;
import com.cloud.utils.exception.CloudRuntimeException;
public class ImageMotionServiceImpl implements ImageMotionService {
@Inject
List<ImageMotionStrategy> motionStrategies;
@Inject
VolumeService volumeService;
@Inject
ImageService imageService;
@Override
public boolean copyIso(String isoUri, String destIsoUri) {
// TODO Auto-generated method stub
@ -30,9 +47,23 @@ public class ImageMotionServiceImpl implements ImageMotionService {
}
@Override
public boolean copyTemplate(TemplateEntity template, PrimaryDataStoreInfo dataStore) {
// TODO Auto-generated method stub
return false;
}
public boolean copyTemplate(TemplateInfo template, VolumeInfo volume) {
ImageMotionStrategy ims = null;
for (ImageMotionStrategy strategy : motionStrategies) {
if (strategy.canHandle(template, volume)) {
ims = strategy;
break;
}
}
if (ims == null) {
throw new CloudRuntimeException("Can't find proper image motion strategy");
}
EndPoint ep = ims.getEndPoint(template, volume);
volumeService.grantAccess(volume, ep);
imageService.grantTemplateAccess(template, ep);
return ims.copyTemplate(template, volume, ep);
}
}

View File

@ -19,14 +19,13 @@
package org.apache.cloudstack.storage.image.motion;
import org.apache.cloudstack.engine.cloud.entity.api.TemplateEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.image.TemplateInfo;
public class DefaultImageMotionProvider implements ImageMotionProvider {
@Override
public boolean canHandle(TemplateEntity template, PrimaryDataStore dataStoe) {
// TODO Auto-generated method stub
return false;
}
public interface ImageMotionStrategy {
public boolean canHandle(TemplateInfo template, VolumeInfo volume);
public EndPoint getEndPoint(TemplateInfo template, VolumeInfo volume);
public boolean copyTemplate(TemplateInfo template, VolumeInfo volume, EndPoint ep);
}

View File

@ -0,0 +1,9 @@
package org.apache.cloudstack.storage.to;
import org.apache.cloudstack.storage.image.store.ImageDataStoreInfo;
public class ImageDataStoreTO {
public ImageDataStoreTO(ImageDataStoreInfo dataStore) {
}
}

View File

@ -0,0 +1,9 @@
package org.apache.cloudstack.storage.to;
import org.apache.cloudstack.engine.subsystem.api.storage.PrimaryDataStoreInfo;
public class PrimaryDataStoreTO {
public PrimaryDataStoreTO(PrimaryDataStoreInfo dataStore) {
}
}

View File

@ -0,0 +1,9 @@
package org.apache.cloudstack.storage.to;
import org.apache.cloudstack.storage.image.TemplateInfo;
public class TemplateTO {
public TemplateTO(TemplateInfo template) {
}
}

View File

@ -0,0 +1,9 @@
package org.apache.cloudstack.storage.to;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
public class VolumeTO {
public VolumeTO(VolumeInfo volume) {
}
}

View File

@ -19,6 +19,7 @@
package org.apache.cloudstack.storage.volume;
import org.apache.cloudstack.engine.cloud.entity.api.VolumeEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
import org.apache.cloudstack.engine.subsystem.api.storage.type.VolumeType;
@ -60,12 +61,14 @@ public interface VolumeService {
/**
*
*/
String grantAccess(long volumeId, long endpointId);
String grantAccess(VolumeInfo volume, EndPoint endpointId);
/**
*
*/
boolean rokeAccess(long volumeId, long endpointId);
VolumeInfo startCopying(VolumeInfo volume);
VolumeInfo copyingSucceed(VolumeInfo volume);
VolumeInfo copyingFailed(VolumeInfo volume);
VolumeEntity getVolumeEntity(long volumeId);
}

View File

@ -21,6 +21,7 @@ package org.apache.cloudstack.storage.volume;
import javax.inject.Inject;
import org.apache.cloudstack.engine.cloud.entity.api.VolumeEntity;
import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.disktype.VolumeDiskType;
import org.apache.cloudstack.engine.subsystem.api.storage.type.VolumeType;
@ -86,12 +87,6 @@ public class VolumeServiceImpl implements VolumeService {
return false;
}
@Override
public String grantAccess(long volumeId, long endpointId) {
// TODO Auto-generated method stub
return null;
}
@Override
public boolean rokeAccess(long volumeId, long endpointId) {
// TODO Auto-generated method stub
@ -118,4 +113,28 @@ public class VolumeServiceImpl implements VolumeService {
return new VolumeEntityImpl(dataStore.getVolume(volumeId));
}
}
@Override
public String grantAccess(VolumeInfo volume, EndPoint endpointId) {
// TODO Auto-generated method stub
return null;
}
@Override
public VolumeInfo startCopying(VolumeInfo volume) {
// TODO Auto-generated method stub
return null;
}
@Override
public VolumeInfo copyingSucceed(VolumeInfo volume) {
// TODO Auto-generated method stub
return null;
}
@Override
public VolumeInfo copyingFailed(VolumeInfo volume) {
// TODO Auto-generated method stub
return null;
}
}