From cf68dfb43085ae40da021e9d9fc42b31b5aa6666 Mon Sep 17 00:00:00 2001 From: abhishek Date: Wed, 25 Aug 2010 15:33:06 -0700 Subject: [PATCH] Refactored detach iso command --- .../com/cloud/api/commands/DetachIsoCmd.java | 130 ++++++++--------- .../com/cloud/server/ManagementServer.java | 6 +- .../cloud/server/ManagementServerImpl.java | 138 +++++++++--------- .../com/cloud/template/TemplateManager.java | 2 + .../cloud/template/TemplateManagerImpl.java | 108 +++++++++++++- 5 files changed, 241 insertions(+), 143 deletions(-) diff --git a/server/src/com/cloud/api/commands/DetachIsoCmd.java b/server/src/com/cloud/api/commands/DetachIsoCmd.java index 132ebfe4549..f3f40b6582d 100644 --- a/server/src/com/cloud/api/commands/DetachIsoCmd.java +++ b/server/src/com/cloud/api/commands/DetachIsoCmd.java @@ -18,30 +18,18 @@ package com.cloud.api.commands; -import java.util.ArrayList; -import java.util.List; -import java.util.Map; - import org.apache.log4j.Logger; -import com.cloud.api.BaseCmd; +import com.cloud.api.BaseAsyncCmd; +import com.cloud.api.Implementation; import com.cloud.api.Parameter; -import com.cloud.api.ServerApiException; -import com.cloud.user.Account; -import com.cloud.utils.Pair; -import com.cloud.vm.UserVmVO; - -public class DetachIsoCmd extends BaseCmd { +import com.cloud.api.BaseCmd.Manager; + +@Implementation(method="detachIso", manager=Manager.TemplateManager) +public class DetachIsoCmd extends BaseAsyncCmd { public static final Logger s_logger = Logger.getLogger(DetachIsoCmd.class.getName()); private static final String s_name = "detachisoresponse"; - private static final List> s_properties = new ArrayList>(); - - static { - s_properties.add(new Pair(BaseCmd.Properties.VIRTUAL_MACHINE_ID, Boolean.TRUE)); - s_properties.add(new Pair(BaseCmd.Properties.ACCOUNT_OBJ, Boolean.FALSE)); - s_properties.add(new Pair(BaseCmd.Properties.USER_ID, Boolean.FALSE)); - } ///////////////////////////////////////////////////// //////////////// API parameters ///////////////////// @@ -68,59 +56,61 @@ public class DetachIsoCmd extends BaseCmd { public String getName() { return s_name; } - - @Override - public List> getProperties() { - return s_properties; - } - @Override - public List> execute(Map params) { - Account account = (Account) params.get(BaseCmd.Properties.ACCOUNT_OBJ.getName()); - Long userId = (Long) params.get(BaseCmd.Properties.USER_ID.getName()); - Long vmId = (Long) params.get(BaseCmd.Properties.VIRTUAL_MACHINE_ID.getName()); +// @Override +// public List> execute(Map params) { +// Account account = (Account) params.get(BaseCmd.Properties.ACCOUNT_OBJ.getName()); +// Long userId = (Long) params.get(BaseCmd.Properties.USER_ID.getName()); +// Long vmId = (Long) params.get(BaseCmd.Properties.VIRTUAL_MACHINE_ID.getName()); +// +// // Verify input parameters +// UserVmVO vmInstanceCheck = getManagementServer().findUserVMInstanceById(vmId.longValue()); +// if (vmInstanceCheck == null) { +// throw new ServerApiException (BaseCmd.VM_INVALID_PARAM_ERROR, "Unable to find a virtual machine with id " + vmId); +// } +// +// if (account != null) { +// if (!isAdmin(account.getType())) { +// if (account.getId().longValue() != vmInstanceCheck.getAccountId()) { +// throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + " for this account"); +// } +// } else if (!getManagementServer().isChildDomain(account.getDomainId(), vmInstanceCheck.getDomainId())) { +// throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + ", permission denied."); +// } +// } +// +// // If command is executed via 8096 port, set userId to the id of System account (1) +// if (userId == null) +// userId = new Long(1); +// +// try { +// long jobId = getManagementServer().detachISOFromVMAsync(vmId.longValue(), userId); +// +// if (jobId == 0) { +// s_logger.warn("Unable to schedule async-job for AttachIsoCmd"); +// } else { +// if(s_logger.isDebugEnabled()) +// s_logger.debug("AttachIsoCmd has been accepted, job id: " + jobId); +// } +// +// List> returnValues = new ArrayList>(); +// returnValues.add(new Pair(BaseCmd.Properties.JOB_ID.getName(), Long.valueOf(jobId))); +// +// return returnValues; +// } catch (ServerApiException apiEx) { +// s_logger.error("Exception detaching ISO", apiEx); +// throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to detach ISO: " + apiEx.getDescription()); +// } catch (Exception ex) { +// s_logger.error("Exception detaching ISO", ex); +// throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to detach ISO: " + ex.getMessage()); +// } +// +// } - // Verify input parameters - UserVmVO vmInstanceCheck = getManagementServer().findUserVMInstanceById(vmId.longValue()); - if (vmInstanceCheck == null) { - throw new ServerApiException (BaseCmd.VM_INVALID_PARAM_ERROR, "Unable to find a virtual machine with id " + vmId); - } - if (account != null) { - if (!isAdmin(account.getType())) { - if (account.getId().longValue() != vmInstanceCheck.getAccountId()) { - throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + " for this account"); - } - } else if (!getManagementServer().isChildDomain(account.getDomainId(), vmInstanceCheck.getDomainId())) { - throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + ", permission denied."); - } - } - - // If command is executed via 8096 port, set userId to the id of System account (1) - if (userId == null) - userId = new Long(1); - - try { - long jobId = getManagementServer().detachISOFromVMAsync(vmId.longValue(), userId); - - if (jobId == 0) { - s_logger.warn("Unable to schedule async-job for AttachIsoCmd"); - } else { - if(s_logger.isDebugEnabled()) - s_logger.debug("AttachIsoCmd has been accepted, job id: " + jobId); - } - - List> returnValues = new ArrayList>(); - returnValues.add(new Pair(BaseCmd.Properties.JOB_ID.getName(), Long.valueOf(jobId))); - - return returnValues; - } catch (ServerApiException apiEx) { - s_logger.error("Exception detaching ISO", apiEx); - throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to detach ISO: " + apiEx.getDescription()); - } catch (Exception ex) { - s_logger.error("Exception detaching ISO", ex); - throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to detach ISO: " + ex.getMessage()); - } - - } + @Override + public String getResponse() { + // TODO Auto-generated method stub + return null; + } } diff --git a/server/src/com/cloud/server/ManagementServer.java b/server/src/com/cloud/server/ManagementServer.java index 2ac51949b0a..002ccd56814 100644 --- a/server/src/com/cloud/server/ManagementServer.java +++ b/server/src/com/cloud/server/ManagementServer.java @@ -646,7 +646,7 @@ public interface ManagementServer { */ boolean attachISOToVM(long vmId, long userId, long isoId, boolean attach, long startEventId); long attachISOToVMAsync(long vmId, long userId, long isoId) throws InvalidParameterValueException; - long detachISOFromVMAsync(long vmId, long userId) throws InvalidParameterValueException; +// long detachISOFromVMAsync(long vmId, long userId) throws InvalidParameterValueException; /** * Creates and starts a new Virtual Machine. @@ -1126,8 +1126,8 @@ public interface ManagementServer { * @param zoneId * @return true if success */ - boolean deleteTemplate(long userId, long templateId, Long zoneId, long startEventId) throws InternalErrorException; - long deleteTemplateAsync(long userId, long templateId, Long zoneId) throws InvalidParameterValueException; +// boolean deleteTemplate(long userId, long templateId, Long zoneId, long startEventId) throws InternalErrorException; +// long deleteTemplateAsync(long userId, long templateId, Long zoneId) throws InvalidParameterValueException; /** * Copies a template from one secondary storage server to another diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java index e4fddbf6301..86d5c9d1382 100755 --- a/server/src/com/cloud/server/ManagementServerImpl.java +++ b/server/src/com/cloud/server/ManagementServerImpl.java @@ -2215,35 +2215,35 @@ public class ManagementServerImpl implements ManagementServer { return _asyncMgr.submitAsyncJob(job, true); } - @Override - public long detachISOFromVMAsync(long vmId, long userId) throws InvalidParameterValueException { - UserVm userVM = _userVmDao.findById(vmId); - if (userVM == null) { - throw new InvalidParameterValueException("Please specify a valid VM."); - } - - Long isoId = userVM.getIsoId(); - if (isoId == null) { - throw new InvalidParameterValueException("The specified VM has no ISO attached to it."); - } - - State vmState = userVM.getState(); - if (vmState != State.Running && vmState != State.Stopped) { - throw new InvalidParameterValueException("Please specify a VM that is either Stopped or Running."); - } - - long eventId = EventUtils.saveScheduledEvent(userId, userVM.getAccountId(), EventTypes.EVENT_ISO_DETACH, "detaching ISO: "+isoId+" from Vm: "+vmId); - AttachISOParam param = new AttachISOParam(vmId, userId, isoId.longValue(), false); - param.setEventId(eventId); - Gson gson = GsonHelper.getBuilder().create(); - - AsyncJobVO job = new AsyncJobVO(); - job.setUserId(UserContext.current().getUserId()); - job.setAccountId(userVM.getAccountId()); - job.setCmd("AttachISO"); - job.setCmdInfo(gson.toJson(param)); - return _asyncMgr.submitAsyncJob(job, true); - } +// @Override +// public long detachISOFromVMAsync(long vmId, long userId) throws InvalidParameterValueException { +// UserVm userVM = _userVmDao.findById(vmId); +// if (userVM == null) { +// throw new InvalidParameterValueException("Please specify a valid VM."); +// } +// +// Long isoId = userVM.getIsoId(); +// if (isoId == null) { +// throw new InvalidParameterValueException("The specified VM has no ISO attached to it."); +// } +// +// State vmState = userVM.getState(); +// if (vmState != State.Running && vmState != State.Stopped) { +// throw new InvalidParameterValueException("Please specify a VM that is either Stopped or Running."); +// } +// +// long eventId = EventUtils.saveScheduledEvent(userId, userVM.getAccountId(), EventTypes.EVENT_ISO_DETACH, "detaching ISO: "+isoId+" from Vm: "+vmId); +// AttachISOParam param = new AttachISOParam(vmId, userId, isoId.longValue(), false); +// param.setEventId(eventId); +// Gson gson = GsonHelper.getBuilder().create(); +// +// AsyncJobVO job = new AsyncJobVO(); +// job.setUserId(UserContext.current().getUserId()); +// job.setAccountId(userVM.getAccountId()); +// job.setCmd("AttachISO"); +// job.setCmdInfo(gson.toJson(param)); +// return _asyncMgr.submitAsyncJob(job, true); +// } // @Override // public long resetVMPasswordAsync(long userId, long vmId, String password) { @@ -4774,47 +4774,47 @@ public class ManagementServerImpl implements ManagementServer { return _templateDao.update(id, template); } - @Override - public boolean deleteTemplate(long userId, long templateId, Long zoneId, long startEventId) throws InternalErrorException { - return _tmpltMgr.delete(userId, templateId, zoneId, startEventId); - } +// @Override +// public boolean deleteTemplate(long userId, long templateId, Long zoneId, long startEventId) throws InternalErrorException { +// return _tmpltMgr.delete(userId, templateId, zoneId, startEventId); +// } - @Override - public long deleteTemplateAsync(long userId, long templateId, Long zoneId) throws InvalidParameterValueException { - UserVO user = _userDao.findById(userId); - if (user == null) { - throw new InvalidParameterValueException("Please specify a valid user."); - } - - VMTemplateVO template = _templateDao.findById(templateId); - if (template == null) { - throw new InvalidParameterValueException("Please specify a valid template."); - } - - if (template.getFormat() == ImageFormat.ISO) { - throw new InvalidParameterValueException("Please specify a valid template."); - } - - if (template.getUniqueName().equals("routing")) { - throw new InvalidParameterValueException("The DomR template cannot be deleted."); - } - - if (zoneId != null && (_hostDao.findSecondaryStorageHost(zoneId) == null)) { - throw new InvalidParameterValueException("Failed to find a secondary storage host in the specified zone."); - } - - DeleteTemplateParam param = new DeleteTemplateParam(userId, templateId, zoneId, 0); - Gson gson = GsonHelper.getBuilder().create(); - - AsyncJobVO job = new AsyncJobVO(); - job.setUserId(UserContext.current().getUserId()); - job.setAccountId(template.getAccountId()); - job.setCmd("DeleteTemplate"); - job.setCmdInfo(gson.toJson(param)); - job.setCmdOriginator(DeleteTemplateCmd.getStaticName()); - - return _asyncMgr.submitAsyncJob(job); - } +// @Override +// public long deleteTemplateAsync(long userId, long templateId, Long zoneId) throws InvalidParameterValueException { +// UserVO user = _userDao.findById(userId); +// if (user == null) { +// throw new InvalidParameterValueException("Please specify a valid user."); +// } +// +// VMTemplateVO template = _templateDao.findById(templateId); +// if (template == null) { +// throw new InvalidParameterValueException("Please specify a valid template."); +// } +// +// if (template.getFormat() == ImageFormat.ISO) { +// throw new InvalidParameterValueException("Please specify a valid template."); +// } +// +// if (template.getUniqueName().equals("routing")) { +// throw new InvalidParameterValueException("The DomR template cannot be deleted."); +// } +// +// if (zoneId != null && (_hostDao.findSecondaryStorageHost(zoneId) == null)) { +// throw new InvalidParameterValueException("Failed to find a secondary storage host in the specified zone."); +// } +// +// DeleteTemplateParam param = new DeleteTemplateParam(userId, templateId, zoneId, 0); +// Gson gson = GsonHelper.getBuilder().create(); +// +// AsyncJobVO job = new AsyncJobVO(); +// job.setUserId(UserContext.current().getUserId()); +// job.setAccountId(template.getAccountId()); +// job.setCmd("DeleteTemplate"); +// job.setCmdInfo(gson.toJson(param)); +// job.setCmdOriginator(DeleteTemplateCmd.getStaticName()); +// +// return _asyncMgr.submitAsyncJob(job); +// } @Override public boolean copyTemplate(long userId, long templateId, long sourceZoneId, long destZoneId, long startEventId) throws InternalErrorException { diff --git a/server/src/com/cloud/template/TemplateManager.java b/server/src/com/cloud/template/TemplateManager.java index 39becf8b3f5..8ac0dc03943 100644 --- a/server/src/com/cloud/template/TemplateManager.java +++ b/server/src/com/cloud/template/TemplateManager.java @@ -22,6 +22,7 @@ import java.net.URISyntaxException; import java.util.List; import com.cloud.api.commands.CreateTemplateCmd; +import com.cloud.api.commands.DetachIsoCmd; import com.cloud.api.commands.RegisterIsoCmd; import com.cloud.api.commands.RegisterTemplateCmd; import com.cloud.exception.InternalErrorException; @@ -119,6 +120,7 @@ public interface TemplateManager extends Manager { */ boolean delete(long userId, long templateId, Long zoneId, long startEventId) throws InternalErrorException; + boolean detachIso(DetachIsoCmd cmd) throws InternalErrorException, InvalidParameterValueException; /** * Lists templates in the specified storage pool that are not being used by any VM. * @param pool diff --git a/server/src/com/cloud/template/TemplateManagerImpl.java b/server/src/com/cloud/template/TemplateManagerImpl.java index 575cfac664c..14741a5cd99 100644 --- a/server/src/com/cloud/template/TemplateManagerImpl.java +++ b/server/src/com/cloud/template/TemplateManagerImpl.java @@ -23,13 +23,14 @@ import java.net.URI; import java.net.URISyntaxException; import java.net.UnknownHostException; import java.util.ArrayList; -import java.util.HashMap; import java.util.List; import java.util.Map; import javax.ejb.Local; import javax.naming.ConfigurationException; +import org.GNOME.Accessibility._ValueStub; +import org.GNOME.Bonobo._UnknownStub; import org.apache.log4j.Logger; import com.cloud.agent.api.Answer; @@ -39,14 +40,17 @@ import com.cloud.agent.api.storage.PrimaryStorageDownloadCommand; import com.cloud.agent.manager.AgentManager; import com.cloud.api.BaseCmd; import com.cloud.api.ServerApiException; +import com.cloud.api.commands.DetachIsoCmd; import com.cloud.api.commands.RegisterIsoCmd; import com.cloud.api.commands.RegisterTemplateCmd; import com.cloud.configuration.ResourceCount.ResourceType; import com.cloud.configuration.dao.ConfigurationDao; import com.cloud.dc.DataCenterVO; import com.cloud.dc.dao.DataCenterDao; +import com.cloud.domain.dao.DomainDao; import com.cloud.event.EventState; import com.cloud.event.EventTypes; +import com.cloud.event.EventUtils; import com.cloud.event.EventVO; import com.cloud.event.dao.EventDao; import com.cloud.exception.InternalErrorException; @@ -85,6 +89,7 @@ import com.cloud.user.UserVO; import com.cloud.user.dao.AccountDao; import com.cloud.user.dao.UserAccountDao; import com.cloud.user.dao.UserDao; +import com.cloud.uservm.UserVm; import com.cloud.utils.EnumUtils; import com.cloud.utils.NumbersUtil; import com.cloud.utils.component.ComponentLocator; @@ -94,7 +99,11 @@ import com.cloud.utils.db.SearchBuilder; import com.cloud.utils.db.SearchCriteria; import com.cloud.utils.db.Transaction; import com.cloud.utils.exception.CloudRuntimeException; +import com.cloud.vm.State; +import com.cloud.vm.UserVmManager; +import com.cloud.vm.UserVmVO; import com.cloud.vm.VMInstanceVO; +import com.cloud.vm.dao.UserVmDao; import com.cloud.vm.dao.VMInstanceDao; @Local(value=TemplateManager.class) @@ -117,10 +126,13 @@ public class TemplateManagerImpl implements TemplateManager { @Inject AccountManager _accountMgr; @Inject HostDao _hostDao; @Inject DataCenterDao _dcDao; + @Inject UserVmDao _userVmDao; @Inject VolumeDao _volumeDao; @Inject SnapshotDao _snapshotDao; + @Inject DomainDao _domainDao; long _routerTemplateId = -1; @Inject StorageManager _storageMgr; + @Inject UserVmManager _vmMgr; @Inject ConfigurationDao _configDao; protected SearchBuilder HostTemplateStatesSearch; @@ -868,4 +880,98 @@ public class TemplateManagerImpl implements TemplateManager { return true; } + + @Override + public boolean detachIso(DetachIsoCmd cmd) throws InternalErrorException, InvalidParameterValueException { + Account account = (Account) UserContext.current().getAccountObject(); + Long userId = UserContext.current().getUserId(); + Long vmId = cmd.getVirtualMachineId(); + + // Verify input parameters + UserVmVO vmInstanceCheck = _userVmDao.findById(vmId.longValue()); + if (vmInstanceCheck == null) { + throw new ServerApiException (BaseCmd.VM_INVALID_PARAM_ERROR, "Unable to find a virtual machine with id " + vmId); + } + + userId = accountAndUserValidation(account, userId, vmInstanceCheck); + + UserVm userVM = _userVmDao.findById(vmId); + if (userVM == null) { + throw new InvalidParameterValueException("Please specify a valid VM."); + } + + Long isoId = userVM.getIsoId(); + if (isoId == null) { + throw new InvalidParameterValueException("The specified VM has no ISO attached to it."); + } + + State vmState = userVM.getState(); + if (vmState != State.Running && vmState != State.Stopped) { + throw new InvalidParameterValueException("Please specify a VM that is either Stopped or Running."); + } + + return attachISOToVM(vmId, userId, isoId, false); //attach=false => detach + + } + + private boolean attachISOToVM(long vmId, long userId, long isoId, boolean attach) { + UserVmVO vm = _userVmDao.findById(vmId); + VMTemplateVO iso = _tmpltDao.findById(isoId); + long startEventId = 0; + if(attach){ + startEventId = EventUtils.saveStartedEvent(userId, vm.getAccountId(), EventTypes.EVENT_ISO_ATTACH, "Attaching ISO: "+isoId+" to Vm: "+vmId, startEventId); + } else { + startEventId = EventUtils.saveStartedEvent(userId, vm.getAccountId(), EventTypes.EVENT_ISO_DETACH, "Detaching ISO: "+isoId+" from Vm: "+vmId, startEventId); + } + boolean success = _vmMgr.attachISOToVM(vmId, isoId, attach); + + if (success) { + if (attach) { + vm.setIsoId(iso.getId().longValue()); + } else { + vm.setIsoId(null); + } + _userVmDao.update(vmId, vm); + + if (attach) { + EventUtils.saveEvent(userId, vm.getAccountId(), EventVO.LEVEL_INFO, EventTypes.EVENT_ISO_ATTACH, "Successfully attached ISO: " + iso.getName() + " to VM with ID: " + vmId, + null, startEventId); + } else { + EventUtils.saveEvent(userId, vm.getAccountId(), EventVO.LEVEL_INFO, EventTypes.EVENT_ISO_DETACH, "Successfully detached ISO from VM with ID: " + vmId, null, startEventId); + } + } else { + if (attach) { + EventUtils.saveEvent(userId, vm.getAccountId(), EventVO.LEVEL_ERROR, EventTypes.EVENT_ISO_ATTACH, "Failed to attach ISO: " + iso.getName() + " to VM with ID: " + vmId, null, startEventId); + } else { + EventUtils.saveEvent(userId, vm.getAccountId(), EventVO.LEVEL_ERROR, EventTypes.EVENT_ISO_DETACH, "Failed to detach ISO from VM with ID: " + vmId, null, startEventId); + } + } + + return success; + } + + private Long accountAndUserValidation(Account account, Long userId, + UserVmVO vmInstanceCheck) { + if (account != null) { + if (!isAdmin(account.getType())) { + if (account.getId().longValue() != vmInstanceCheck.getAccountId()) { + throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + " for this account"); + } + } else if (!_domainDao.isChildDomain(account.getDomainId(), vmInstanceCheck.getDomainId())) { + throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, "Unable to detach ISO from virtual machine " + vmInstanceCheck.getName() + ", permission denied."); + } + } + + // If command is executed via 8096 port, set userId to the id of System account (1) + if (userId == null) + userId = new Long(1); + + return userId; + } + + private static boolean isAdmin(short accountType) { + return ((accountType == Account.ACCOUNT_TYPE_ADMIN) || + (accountType == Account.ACCOUNT_TYPE_DOMAIN_ADMIN) || + (accountType == Account.ACCOUNT_TYPE_READ_ONLY_ADMIN)); + } }