Maor Lipchuk has uploaded a new change for review. Change subject: core: Support detach Storage Domain with disks. ......................................................................
core: Support detach Storage Domain with disks. Adding support for detaching Storage Domain which contains disks, VMs and Templates. Change-Id: I971fe6acd4a2667a09487c5e1108cf7c759587f1 Signed-off-by: Maor Lipchuk <[email protected]> --- M backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/DetachStorageDomainFromPoolCommand.java M backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/StorageDomainCommandBase.java M backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/AuditLogType.java M backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java M backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dal/dbbroker/auditloghandling/AuditLogDirector.java M backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAO.java M backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAODbFacadeImpl.java M backend/manager/modules/dal/src/main/resources/bundles/AppErrors.properties M backend/manager/modules/dal/src/main/resources/bundles/AuditLogMessages.properties M backend/manager/modules/dal/src/test/java/org/ovirt/engine/core/dao/VmStaticDAOTest.java M frontend/webadmin/modules/frontend/src/main/java/org/ovirt/engine/ui/frontend/AppErrors.java M frontend/webadmin/modules/userportal-gwtp/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties M frontend/webadmin/modules/webadmin/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties M packaging/dbscripts/vms_sp.sql 14 files changed, 83 insertions(+), 19 deletions(-) git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/86/24286/1 diff --git a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/DetachStorageDomainFromPoolCommand.java b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/DetachStorageDomainFromPoolCommand.java index 78b1ea9..77e23ab 100644 --- a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/DetachStorageDomainFromPoolCommand.java +++ b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/DetachStorageDomainFromPoolCommand.java @@ -1,12 +1,15 @@ package org.ovirt.engine.core.bll.storage; +import java.util.List; + +import org.apache.commons.lang.StringUtils; import org.ovirt.engine.core.bll.NonTransactiveCommandAttribute; import org.ovirt.engine.core.common.AuditLogType; import org.ovirt.engine.core.common.action.DetachStorageDomainFromPoolParameters; import org.ovirt.engine.core.common.businessentities.StorageDomainStatus; import org.ovirt.engine.core.common.businessentities.StorageDomainType; -import org.ovirt.engine.core.common.businessentities.StoragePoolIsoMapId; import org.ovirt.engine.core.common.businessentities.StoragePoolIsoMap; +import org.ovirt.engine.core.common.businessentities.StoragePoolIsoMapId; import org.ovirt.engine.core.common.errors.VdcBllMessages; import org.ovirt.engine.core.common.vdscommands.DetachStorageDomainVDSCommandParameters; import org.ovirt.engine.core.common.vdscommands.IrsBaseVDSCommandParameters; @@ -14,6 +17,7 @@ import org.ovirt.engine.core.common.vdscommands.VDSReturnValue; import org.ovirt.engine.core.compat.Guid; import org.ovirt.engine.core.dal.dbbroker.DbFacade; +import org.ovirt.engine.core.dal.dbbroker.auditloghandling.AuditLogDirector; import org.ovirt.engine.core.utils.transaction.TransactionMethod; import org.ovirt.engine.core.utils.transaction.TransactionSupport; @@ -37,6 +41,10 @@ @Override protected void executeCommand() { log.info("Start detach storage domain"); + if (!canStorageDomainBeDetached()) { + setSucceeded(Boolean.FALSE.booleanValue()); + return; + } changeStorageDomainStatusInTransaction(getStorageDomain().getStoragePoolIsoMapData(), StorageDomainStatus.Locked); log.info(" Detach storage domain: before connect"); @@ -75,6 +83,18 @@ setSucceeded(returnValue.getSucceeded()); } + private boolean canStorageDomainBeDetached() { + List<String> vmNames = getVmStaticDAO().getAllVMsWithDisksOnOtherStorageDomain(getStorageDomain().getId()); + if (!vmNames.isEmpty()) { + log.errorFormat("Failed to remove Storage Domain {1} since there are vms which contain disks related to other storage domains.", + getStorageDomain().getId()); + this.addCustomValue("vmsNames", StringUtils.join(vmNames, ",")); + AuditLogDirector.log(this, AuditLogType.DETACH_STORAGE_DOMAIN_WITH_RELATED_VMS); + return false; + } + return true; + } + @Override public AuditLogType getAuditLogTypeValue() { return getSucceeded() ? AuditLogType.USER_DETACH_STORAGE_DOMAIN_FROM_POOL diff --git a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/StorageDomainCommandBase.java b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/StorageDomainCommandBase.java index 4b47c89..5a8a99f 100644 --- a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/StorageDomainCommandBase.java +++ b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/storage/StorageDomainCommandBase.java @@ -78,9 +78,6 @@ if (getStoragePoolIsoMap() == null) { returnValue = false; addCanDoActionMessage(VdcBllMessages.STORAGE_DOMAIN_NOT_ATTACHED_TO_STORAGE_POOL); - } else if (hasImages()) { - returnValue = false; - addCanDoActionMessage(VdcBllMessages.ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES); } else if (!isRemoveLast && isMaster()) { diff --git a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/AuditLogType.java b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/AuditLogType.java index 755bf03..74aa735 100644 --- a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/AuditLogType.java +++ b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/AuditLogType.java @@ -738,6 +738,7 @@ UPDATE_OVF_FOR_STORAGE_POOL_FAILED(1005), UPGRADE_STORAGE_POOL_ENCOUNTERED_PROBLEMS(1006), REFRESH_REPOSITORY_IMAGE_LIST_INCOMPLETE(1007), + DETACH_STORAGE_DOMAIN_WITH_RELATED_VMS(1008), RELOAD_CONFIGURATIONS_SUCCESS(1010), RELOAD_CONFIGURATIONS_FAILURE(1011), diff --git a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java index d942e50..e246660 100644 --- a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java +++ b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java @@ -554,7 +554,6 @@ ACTION_TYPE_FAILED_STORAGE_DOMAIN_FORMAT_ILLEGAL_HOST(ErrorType.CONFLICT), ACTION_TYPE_FAILED_MASTER_STORAGE_DOMAIN_NOT_ACTIVE(ErrorType.CONFLICT), STORAGE_DOMAIN_NOT_ATTACHED_TO_STORAGE_POOL(ErrorType.CONFLICT), - ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES(ErrorType.CONFLICT), ERROR_CANNOT_ATTACH_MORE_THAN_ONE_ISO_DOMAIN(ErrorType.CONFLICT), ERROR_CANNOT_ATTACH_MORE_THAN_ONE_EXPORT_DOMAIN(ErrorType.CONFLICT), ERROR_CANNOT_DETACH_LAST_STORAGE_DOMAIN(ErrorType.CONFLICT), diff --git a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dal/dbbroker/auditloghandling/AuditLogDirector.java b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dal/dbbroker/auditloghandling/AuditLogDirector.java index 4cacf47..7af389f 100644 --- a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dal/dbbroker/auditloghandling/AuditLogDirector.java +++ b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dal/dbbroker/auditloghandling/AuditLogDirector.java @@ -405,6 +405,7 @@ severities.put(AuditLogType.SYSTEM_FAILED_CHANGE_STORAGE_POOL_STATUS, AuditLogSeverity.ERROR); severities.put(AuditLogType.SYSTEM_CHANGE_STORAGE_POOL_STATUS_NO_HOST_FOR_SPM, AuditLogSeverity.ERROR); severities.put(AuditLogType.SYSTEM_CHANGE_STORAGE_POOL_STATUS_PROBLEMATIC, AuditLogSeverity.WARNING); + severities.put(AuditLogType.DETACH_STORAGE_DOMAIN_WITH_RELATED_VMS, AuditLogSeverity.ERROR); severities.put(AuditLogType.SYSTEM_CHANGE_STORAGE_POOL_STATUS_PROBLEMATIC_SEARCHING_NEW_SPM, AuditLogSeverity.WARNING); severities diff --git a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAO.java b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAO.java index 9dfa337..474a6f2 100644 --- a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAO.java +++ b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAO.java @@ -63,6 +63,15 @@ List<String> getAllNamesPinnedToHost(Guid host); /** + * Retrieves all VM names which contains disks on other Storage Domain other then the storageDomain GUID. + * + * @param storageDomainGuid + * the storage domain GUID + * @return List of VMs + */ + List<String> getAllVMsWithDisksOnOtherStorageDomain(Guid storageDomainGuid); + + /** * get the db generation for vm/template with the given guid * * @param id - vm/template id diff --git a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAODbFacadeImpl.java b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAODbFacadeImpl.java index 38eed38..d581d85 100644 --- a/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAODbFacadeImpl.java +++ b/backend/manager/modules/dal/src/main/java/org/ovirt/engine/core/dao/VmStaticDAODbFacadeImpl.java @@ -168,6 +168,21 @@ } @Override + public List<String> getAllVMsWithDisksOnOtherStorageDomain(Guid storageDomainGuid) { + RowMapper<String> mapper = new RowMapper<String>() { + + @Override + public String mapRow(ResultSet rs, int rowNum) throws SQLException { + return rs.getString("vm_name"); + } + }; + + return getCallsHandler().executeReadList("getAllVMsWithDisksOnOtherStorageDomain", mapper, + getCustomMapSqlParameterSource() + .addValue("storage_domain_id", storageDomainGuid)); + } + + @Override public void incrementDbGenerationForAllInStoragePool(Guid storagePoolId) { getCallsHandler().executeModification("IncrementDbGenerationForAllInStoragePool", getCustomMapSqlParameterSource() .addValue("storage_pool_id", storagePoolId)); diff --git a/backend/manager/modules/dal/src/main/resources/bundles/AppErrors.properties b/backend/manager/modules/dal/src/main/resources/bundles/AppErrors.properties index 5ee8d23..81c7c34 100644 --- a/backend/manager/modules/dal/src/main/resources/bundles/AppErrors.properties +++ b/backend/manager/modules/dal/src/main/resources/bundles/AppErrors.properties @@ -453,8 +453,6 @@ ACTION_TYPE_FAILED_STORAGE_DOMAIN_NOT_IN_STORAGE_POOL=Cannot ${action} ${type}. The selected Storage Domain is not part of the Data Center. ACTION_TYPE_FAILED_LUNS_ALREADY_PART_OF_STORAGE_DOMAINS=Cannot ${action} ${type}. The following LUNs are already part of existing storage domains: ${lunIds}. ACTION_TYPE_FAILED_LUNS_ALREADY_USED_BY_DISKS=Cannot ${action} ${type}. The following LUNs are already used by DirectLUN disks: ${lunIds}. -ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES=Cannot detach a non empty Storage Domain.\n\ - -Please remove all VMs / Templates / Disks and try again. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_IMAGES=Cannot remove Data Center while it contains disks.\n\ -Please remove them first. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_VMS=Cannot remove Data Center while there are VMs on it.\n\ diff --git a/backend/manager/modules/dal/src/main/resources/bundles/AuditLogMessages.properties b/backend/manager/modules/dal/src/main/resources/bundles/AuditLogMessages.properties index ea9cff0..bb4e8a0 100644 --- a/backend/manager/modules/dal/src/main/resources/bundles/AuditLogMessages.properties +++ b/backend/manager/modules/dal/src/main/resources/bundles/AuditLogMessages.properties @@ -585,6 +585,7 @@ REFRESH_REPOSITORY_IMAGE_LIST_FAILED=Refresh image list failed for domain(s): ${imageDomains}. Please check domain activity. REFRESH_REPOSITORY_IMAGE_LIST_SUCCEEDED=Refresh image list succeeded for domain(s): ${imageDomains} REFRESH_REPOSITORY_IMAGE_LIST_INCOMPLETE=Refresh image list probably incomplete for domain ${imageDomain}, only ${imageListSize} images discovered. +DETACH_STORAGE_DOMAIN_WITH_RELATED_VMS=Storage Domain ${StorageDomainName} Could not be detached from Data Center ${StoragePoolName} since the following VM(s) contain disks on other storage domains: ${vmsNames}. TASK_CLEARING_ASYNC_TASK=Clearing asynchronous task ${CommandName} that started at ${Date} VM_WAS_SET_DOWN_DUE_TO_HOST_REBOOT_OR_MANUAL_FENCE=Vm ${VmName} was shut down due to ${VdsName} host reboot or manual fence UPDATE_TAGS_VM_DEFAULT_DISPLAY_TYPE=Vm ${VmName} tag default display type was updated diff --git a/backend/manager/modules/dal/src/test/java/org/ovirt/engine/core/dao/VmStaticDAOTest.java b/backend/manager/modules/dal/src/test/java/org/ovirt/engine/core/dao/VmStaticDAOTest.java index 0d27169..7accf3b 100644 --- a/backend/manager/modules/dal/src/test/java/org/ovirt/engine/core/dao/VmStaticDAOTest.java +++ b/backend/manager/modules/dal/src/test/java/org/ovirt/engine/core/dao/VmStaticDAOTest.java @@ -416,4 +416,17 @@ return returnValue; } + + /** + * Ensures that there are no VMs with disks on different storage domains. + */ + @Test + public void testGetAllVMsWithDisksOnOtherStorageDomain() { + List<String> result = dao.getAllVMsWithDisksOnOtherStorageDomain(FixturesTool.STORAGE_DOAMIN_SCALE_SD5); + + assertNotNull(result); + assertFalse(result.isEmpty()); + } + + } diff --git a/frontend/webadmin/modules/frontend/src/main/java/org/ovirt/engine/ui/frontend/AppErrors.java b/frontend/webadmin/modules/frontend/src/main/java/org/ovirt/engine/ui/frontend/AppErrors.java index a8c0de8..4a3ef48 100644 --- a/frontend/webadmin/modules/frontend/src/main/java/org/ovirt/engine/ui/frontend/AppErrors.java +++ b/frontend/webadmin/modules/frontend/src/main/java/org/ovirt/engine/ui/frontend/AppErrors.java @@ -1252,9 +1252,6 @@ @DefaultStringValue("Cannot ${action} ${type}. The following LUNs are already used by DirectLUN disks: ${lunIds}.") String ACTION_TYPE_FAILED_LUNS_ALREADY_USED_BY_DISKS(); - @DefaultStringValue("Cannot detach a non empty Storage Domain.\n-Please remove all VMs / Templates / Disks and try again.") - String ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES(); - @DefaultStringValue("Cannot remove Data Center while it contains disks.\n-Please remove them first.") String ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_IMAGES(); diff --git a/frontend/webadmin/modules/userportal-gwtp/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties b/frontend/webadmin/modules/userportal-gwtp/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties index 13932f1..3e09854 100644 --- a/frontend/webadmin/modules/userportal-gwtp/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties +++ b/frontend/webadmin/modules/userportal-gwtp/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties @@ -426,8 +426,6 @@ ACTION_TYPE_FAILED_STORAGE_DOMAIN_NOT_IN_STORAGE_POOL=Cannot ${action} ${type}. The selected Storage Domain is not part of the Data Center. ACTION_TYPE_FAILED_LUNS_ALREADY_PART_OF_STORAGE_DOMAINS=Cannot ${action} ${type}. The following LUNs are already part of existing storage domains: ${lunIds}. ACTION_TYPE_FAILED_LUNS_ALREADY_USED_BY_DISKS=Cannot ${action} ${type}. The following LUNs are already used by DirectLUN disks: ${lunIds}. -ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES=Cannot detach a non empty Storage Domain.\n\ - -Please remove all VMs / Templates / Disks and try again. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_IMAGES=Cannot remove Data Center while it contains disks.\n\ -Please remove them first. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_VMS=Cannot remove Data Center while there are VMs on it.\n\ diff --git a/frontend/webadmin/modules/webadmin/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties b/frontend/webadmin/modules/webadmin/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties index 5601dcd..c99446a 100644 --- a/frontend/webadmin/modules/webadmin/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties +++ b/frontend/webadmin/modules/webadmin/src/main/resources/org/ovirt/engine/ui/frontend/AppErrors.properties @@ -457,8 +457,6 @@ ACTION_TYPE_FAILED_STORAGE_DOMAIN_NOT_IN_STORAGE_POOL=Cannot ${action} ${type}. The selected Storage Domain is not part of the Data Center. ACTION_TYPE_FAILED_LUNS_ALREADY_PART_OF_STORAGE_DOMAINS=Cannot ${action} ${type}. The following LUNs are already part of existing storage domains: ${lunIds}. ACTION_TYPE_FAILED_LUNS_ALREADY_USED_BY_DISKS=Cannot ${action} ${type}. The following LUNs are already used by DirectLUN disks: ${lunIds}. -ERROR_CANNOT_DETACH_STORAGE_DOMAIN_WITH_IMAGES=Cannot detach a non empty Storage Domain.\n\ - -Please remove all VMs / Templates / Disks and try again. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_IMAGES=Cannot remove Data Center while it contains disks.\n\ -Please remove them first. ERROR_CANNOT_REMOVE_STORAGE_POOL_WITH_VMS=Cannot remove Data Center while there are VMs on it.\n\ diff --git a/packaging/dbscripts/vms_sp.sql b/packaging/dbscripts/vms_sp.sql index 81fb41c..3a9d7e7 100644 --- a/packaging/dbscripts/vms_sp.sql +++ b/packaging/dbscripts/vms_sp.sql @@ -689,9 +689,9 @@ -DROP TYPE IF EXISTS GetNamesOfVmStaticDedicatedToVds_rs CASCADE; -CREATE TYPE GetNamesOfVmStaticDedicatedToVds_rs AS (vm_name CHARACTER VARYING); -Create or replace FUNCTION GetNamesOfVmStaticDedicatedToVds(v_vds_id UUID) RETURNS SETOF GetNamesOfVmStaticDedicatedToVds_rs STABLE +DROP TYPE IF EXISTS GetNamesOfVmStatic_rs CASCADE; +CREATE TYPE GetNamesOfVmStatic_rs AS (vm_name CHARACTER VARYING); +Create or replace FUNCTION GetNamesOfVmStaticDedicatedToVds(v_vds_id UUID) RETURNS SETOF GetNamesOfVmStatic_rs STABLE AS $procedure$ BEGIN RETURN QUERY @@ -1000,8 +1000,25 @@ LANGUAGE plpgsql; - - +Create or replace FUNCTION getAllVMsWithDisksOnOtherStorageDomain(v_storage_domain_id UUID) RETURNS SETOF GetNamesOfVmStatic_rs + AS $procedure$ +BEGIN + RETURN QUERY SELECT DISTINCT vm_static.vm_name + FROM vm_static + INNER JOIN (SELECT vm_static.vm_guid + FROM vm_static + INNER JOIN vm_device vd ON vd.vm_id = vm_static.vm_guid + INNER JOIN images i ON i.image_group_id = vd.device_id + INNER JOIN (SELECT image_id + FROM image_storage_domain_map + WHERE image_storage_domain_map.storage_domain_id = v_storage_domain_id) ISD + ON i.image_guid = ISD.image_id) vms_with_disks_on_storage_domain ON vm_static.vm_guid = vms_with_disks_on_storage_domain.vm_guid + INNER JOIN vm_device vd ON vd.vm_id = vm_static.vm_guid + INNER JOIN images i ON i.image_group_id = vd.device_id + INNER JOIN image_storage_domain_map on i.image_guid = image_storage_domain_map.image_id + WHERE image_storage_domain_map.storage_domain_id <> v_storage_domain_id; +END; $procedure$ +LANGUAGE plpgsql; Create or replace FUNCTION GetActiveVmsByStorageDomainId(v_storage_domain_id UUID) RETURNS SETOF vms STABLE -- To view, visit http://gerrit.ovirt.org/24286 To unsubscribe, visit http://gerrit.ovirt.org/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I971fe6acd4a2667a09487c5e1108cf7c759587f1 Gerrit-PatchSet: 1 Gerrit-Project: ovirt-engine Gerrit-Branch: master Gerrit-Owner: Maor Lipchuk <[email protected]> _______________________________________________ Engine-patches mailing list [email protected] http://lists.ovirt.org/mailman/listinfo/engine-patches
