Shubhendu Tripathi has uploaded a new change for review. Change subject: gluster: BLL Cmd: commit remove bricks async task ......................................................................
gluster: BLL Cmd: commit remove bricks async task BLL command for commiting the remove brick asynchronous task Change-Id: Icbf0e615b067638b56af81e2dabe06512d92d73a Signed-off-by: Shubhendu Tripathi <shtri...@redhat.com> --- A backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommand.java A backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommandTest.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/VdcBllErrors.java M backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllMessages.java M backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/vdscommands/VDSCommandType.java 6 files changed, 354 insertions(+), 0 deletions(-) git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/00/19100/1 diff --git a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommand.java b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommand.java new file mode 100644 index 0000000..e9d8ca9 --- /dev/null +++ b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommand.java @@ -0,0 +1,88 @@ +package org.ovirt.engine.core.bll.gluster; + +import org.ovirt.engine.core.bll.NonTransactiveCommandAttribute; +import org.ovirt.engine.core.bll.interfaces.BackendInternal; +import org.ovirt.engine.core.common.AuditLogType; +import org.ovirt.engine.core.common.action.gluster.GlusterVolumeRemoveBricksParameters; +import org.ovirt.engine.core.common.asynctasks.gluster.GlusterTaskType; +import org.ovirt.engine.core.common.businessentities.gluster.GlusterVolumeEntity; +import org.ovirt.engine.core.common.errors.VdcBllMessages; +import org.ovirt.engine.core.common.job.JobExecutionStatus; +import org.ovirt.engine.core.common.job.StepEnum; +import org.ovirt.engine.core.common.vdscommands.VDSCommandType; +import org.ovirt.engine.core.common.vdscommands.VDSReturnValue; +import org.ovirt.engine.core.common.vdscommands.gluster.GlusterVolumeRemoveBricksVDSParameters; + +/** + * BLL command to stop remove brick asynchronous task started on a gluster volume + */ + +@NonTransactiveCommandAttribute +public class CommitRemoveGlusterVolumeBricksCommand extends GlusterAsyncCommandBase<GlusterVolumeRemoveBricksParameters> { + + public CommitRemoveGlusterVolumeBricksCommand(GlusterVolumeRemoveBricksParameters params) { + super(params); + } + + @Override + protected void setActionMessageParameters() { + addCanDoActionMessage(VdcBllMessages.VAR__ACTION__REMOVE_BRICK_COMMIT); + addCanDoActionMessage(VdcBllMessages.VAR__TYPE__GLUSTER_BRICK); + super.setActionMessageParameters(); + } + + @Override + protected boolean canDoAction() { + GlusterVolumeEntity volume = getGlusterVolume(); + + if (!super.canDoAction()) { + return false; + } + + if (volume.getAsyncTask() == null || volume.getAsyncTask().getType() != GlusterTaskType.REMOVE_BRICK + || volume.getAsyncTask().getStatus() != JobExecutionStatus.FINISHED) { + return failCanDoAction(VdcBllMessages.ACTION_TYPE_FAILED_GLUSTER_VOLUME_REMOVE_BRICK_NOT_STARTED); + } + + return true; + } + + @Override + protected StepEnum getStepType() { + return StepEnum.REMOVING_BRICK; + } + + @Override + protected void executeCommand() { + GlusterVolumeEntity volume = getGlusterVolume(); + VDSReturnValue returnValue = + runVdsCommand(VDSCommandType.CommitRemoveGlusterVolumeBricks, + new GlusterVolumeRemoveBricksVDSParameters(getUpServer().getId(), + volume.getName(), + volume.getBricks(), + volume.getReplicaCount())); + setSucceeded(returnValue.getSucceeded()); + if (!getSucceeded()) { + handleVdsError(AuditLogType.GLUSTER_VOLUME_REMOVE_BRICKS_COMMIT_FAILED, returnValue.getVdsError().getMessage()); + return; + } + + endStepJob(); + releaseVolumeLock(); + getReturnValue().setActionReturnValue(returnValue.getReturnValue()); + } + + @Override + public AuditLogType getAuditLogTypeValue() { + if(getSucceeded()) { + return AuditLogType.GLUSTER_VOLUME_REMOVE_BRICKS_COMMITED; + } else { + return AuditLogType.GLUSTER_VOLUME_REMOVE_BRICKS_COMMIT_FAILED; + } + } + + @Override + public BackendInternal getBackend() { + return super.getBackend(); + } +} diff --git a/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommandTest.java b/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommandTest.java new file mode 100644 index 0000000..b32078d --- /dev/null +++ b/backend/manager/modules/bll/src/test/java/org/ovirt/engine/core/bll/gluster/CommitRemoveGlusterVolumeBricksCommandTest.java @@ -0,0 +1,260 @@ +package org.ovirt.engine.core.bll.gluster; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; +import static org.mockito.Matchers.argThat; +import static org.mockito.Matchers.eq; +import static org.mockito.Mockito.doNothing; +import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.never; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.times; +import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; + +import java.util.ArrayList; +import java.util.List; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.ArgumentMatcher; +import org.mockito.Mock; +import org.mockito.runners.MockitoJUnitRunner; +import org.ovirt.engine.core.bll.interfaces.BackendInternal; +import org.ovirt.engine.core.common.AuditLogType; +import org.ovirt.engine.core.common.action.gluster.GlusterVolumeRemoveBricksParameters; +import org.ovirt.engine.core.common.asynctasks.gluster.GlusterAsyncTask; +import org.ovirt.engine.core.common.asynctasks.gluster.GlusterTaskType; +import org.ovirt.engine.core.common.businessentities.VDS; +import org.ovirt.engine.core.common.businessentities.VDSStatus; +import org.ovirt.engine.core.common.businessentities.gluster.AccessProtocol; +import org.ovirt.engine.core.common.businessentities.gluster.GlusterBrickEntity; +import org.ovirt.engine.core.common.businessentities.gluster.GlusterStatus; +import org.ovirt.engine.core.common.businessentities.gluster.GlusterVolumeEntity; +import org.ovirt.engine.core.common.businessentities.gluster.GlusterVolumeType; +import org.ovirt.engine.core.common.businessentities.gluster.TransportType; +import org.ovirt.engine.core.common.errors.VDSError; +import org.ovirt.engine.core.common.errors.VdcBllErrors; +import org.ovirt.engine.core.common.interfaces.VDSBrokerFrontend; +import org.ovirt.engine.core.common.job.JobExecutionStatus; +import org.ovirt.engine.core.common.vdscommands.VDSCommandType; +import org.ovirt.engine.core.common.vdscommands.VDSParametersBase; +import org.ovirt.engine.core.common.vdscommands.VDSReturnValue; +import org.ovirt.engine.core.common.vdscommands.gluster.GlusterVolumeVDSParameters; +import org.ovirt.engine.core.compat.Guid; +import org.ovirt.engine.core.dao.gluster.GlusterVolumeDao; + +@RunWith(MockitoJUnitRunner.class) +public class CommitRemoveGlusterVolumeBricksCommandTest { + + @Mock + GlusterVolumeDao volumeDao; + @Mock + protected BackendInternal backend; + @Mock + protected VDSBrokerFrontend vdsBrokerFrontend; + + private final Guid volumeWithRemoveBricksTask = new Guid("8bc6f108-c0ef-43ab-ba20-ec41107220f5"); + private final Guid volumeWithRemoveBricksTaskNotFinished = new Guid("b2cb2f73-fab3-4a42-93f0-d5e4c069a43e"); + private final Guid volumeWithoutAsyncTask = new Guid("000000000000-0000-0000-0000-00000003"); + private final Guid volumeWithoutRemoveBricksTask = new Guid("000000000000-0000-0000-0000-00000004"); + private final Guid volumeWithRemoveBricksTaskNull = new Guid("000000000000-0000-0000-0000-00000005"); + private final Guid CLUSTER_ID = new Guid("b399944a-81ab-4ec5-8266-e19ba7c3c9d1"); + + /** + * The command under test. + */ + private CommitRemoveGlusterVolumeBricksCommand cmd; + + private void prepareMocks(CommitRemoveGlusterVolumeBricksCommand command) { + doReturn(volumeDao).when(command).getGlusterVolumeDao(); + doReturn(getVds(VDSStatus.Up)).when(command).getUpServer(); + doReturn(getVolumeWithRemoveBricksTask(volumeWithRemoveBricksTask)).when(volumeDao) + .getById(volumeWithRemoveBricksTask); + doReturn(getVolumeWithRemoveBricksTaskNotFinished(volumeWithRemoveBricksTaskNotFinished)).when(volumeDao) + .getById(volumeWithRemoveBricksTaskNotFinished); + doReturn(getVolume(volumeWithoutAsyncTask)).when(volumeDao).getById(volumeWithoutAsyncTask); + doReturn(getvolumeWithoutRemoveBricksTask(volumeWithoutRemoveBricksTask)).when(volumeDao) + .getById(volumeWithoutRemoveBricksTask); + doReturn(getVolumeWithRemoveBricksTaskNull(volumeWithRemoveBricksTaskNull)).when(volumeDao) + .getById(volumeWithRemoveBricksTaskNull); + doReturn(null).when(volumeDao).getById(null); + } + + private Object getvolumeWithoutRemoveBricksTask(Guid volumeId) { + GlusterVolumeEntity volume = getVolumeWithRemoveBricksTask(volumeId); + volume.getAsyncTask().setType(null); + return volume; + } + + private Object getVolumeWithRemoveBricksTaskNull(Guid volumeId) { + GlusterVolumeEntity volume = getVolume(volumeId); + volume.setAsyncTask(null); + return volume; + } + + private Object getVolumeWithRemoveBricksTaskNotFinished(Guid volumeId) { + GlusterVolumeEntity volume = getVolumeWithRemoveBricksTask(volumeId); + volume.getAsyncTask().setStatus(JobExecutionStatus.STARTED); + return volume; + } + + private GlusterVolumeEntity getVolumeWithRemoveBricksTask(Guid volumeId) { + GlusterVolumeEntity volume = getVolume(volumeId); + GlusterAsyncTask asyncTask = new GlusterAsyncTask(); + asyncTask.setStatus(JobExecutionStatus.FINISHED); + asyncTask.setType(GlusterTaskType.REMOVE_BRICK); + volume.setAsyncTask(asyncTask); + return volume; + } + + private VDS getVds(VDSStatus status) { + VDS vds = new VDS(); + vds.setId(Guid.newGuid()); + vds.setVdsName("gfs1"); + vds.setVdsGroupId(CLUSTER_ID); + vds.setStatus(status); + return vds; + } + + private GlusterVolumeEntity getVolume(Guid id) { + GlusterVolumeEntity volumeEntity = new GlusterVolumeEntity(); + volumeEntity.setId(id); + volumeEntity.setName("test-vol"); + volumeEntity.addAccessProtocol(AccessProtocol.GLUSTER); + volumeEntity.addTransportType(TransportType.TCP); + volumeEntity.setStatus(GlusterStatus.UP); + volumeEntity.setBricks(getBricks(id, 2)); + volumeEntity.setVolumeType(GlusterVolumeType.DISTRIBUTE); + volumeEntity.setClusterId(CLUSTER_ID); + return volumeEntity; + } + + private List<GlusterBrickEntity> getBricks(Guid volumeId, int n) { + List<GlusterBrickEntity> bricks = new ArrayList<GlusterBrickEntity>(); + GlusterBrickEntity brick; + for (Integer i = 0; i < n; i++) { + brick = new GlusterBrickEntity(); + brick.setVolumeId(volumeId); + brick.setBrickDirectory("/tmp/test-vol" + i.toString()); + brick.setStatus(GlusterStatus.UP); + bricks.add(brick); + } + return bricks; + } + + private void mockBackend(boolean succeeded, VdcBllErrors errorCode) { + when(cmd.getBackend()).thenReturn(backend); + when(backend.getResourceManager()).thenReturn(vdsBrokerFrontend); + doNothing().when(cmd).endStepJob(); + doNothing().when(cmd).releaseVolumeLock(); + + VDSReturnValue vdsReturnValue = new VDSReturnValue(); + vdsReturnValue.setSucceeded(succeeded); + if (!succeeded) { + vdsReturnValue.setVdsError(new VDSError(errorCode, "")); + } else { + GlusterAsyncTask task = new GlusterAsyncTask(); + task.setMessage("successful"); + task.setStatus(JobExecutionStatus.FINISHED); + task.setStepId(Guid.newGuid()); + task.setTaskId(Guid.newGuid()); + task.setType(GlusterTaskType.REMOVE_BRICK); + + vdsReturnValue.setReturnValue(task); + } + + when(vdsBrokerFrontend.RunVdsCommand(eq(VDSCommandType.CommitRemoveGlusterVolumeBricks), + argThat(anyGlusterVolumeVDS()))).thenReturn(vdsReturnValue); + } + + private ArgumentMatcher<VDSParametersBase> anyGlusterVolumeVDS() { + return new ArgumentMatcher<VDSParametersBase>() { + + @Override + public boolean matches(Object argument) { + if (!(argument instanceof GlusterVolumeVDSParameters)) { + return false; + } + return true; + } + }; + } + + @Test + public void testExecuteCommand() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithRemoveBricksTask, + getBricks(volumeWithRemoveBricksTask, 2)))); + prepareMocks(cmd); + mockBackend(true, null); + assertTrue(cmd.canDoAction()); + cmd.executeCommand(); + + verify(cmd, times(1)).endStepJob(); + verify(cmd, times(1)).releaseVolumeLock(); + assertEquals(cmd.getAuditLogTypeValue(), AuditLogType.GLUSTER_VOLUME_REMOVE_BRICKS_COMMITED); + } + + @Test + public void executeCommandWhenFailed() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithRemoveBricksTask, + getBricks(volumeWithRemoveBricksTask, 2)))); + prepareMocks(cmd); + mockBackend(false, VdcBllErrors.GlusterVolumeRemoveBricksCommitFailed); + assertTrue(cmd.canDoAction()); + cmd.executeCommand(); + + verify(cmd, never()).endStepJob(); + verify(cmd, never()).releaseVolumeLock(); + assertEquals(cmd.getAuditLogTypeValue(), AuditLogType.GLUSTER_VOLUME_REMOVE_BRICKS_COMMIT_FAILED); + } + + @Test + public void canDoActionSucceedsOnVolumeWithRemoveBricksTask() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithRemoveBricksTask, + getBricks(volumeWithRemoveBricksTask, 2)))); + + prepareMocks(cmd); + assertTrue(cmd.canDoAction()); + } + + @Test + public void canDoActionFailsOnVolumeWithoutAsyncTask() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithoutAsyncTask, + getBricks(volumeWithoutAsyncTask, 2)))); + prepareMocks(cmd); + assertFalse(cmd.canDoAction()); + } + + @Test + public void canDoActionFailsOnVolumeWithoutRemoveBricksTask() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithoutRemoveBricksTask, + getBricks(volumeWithoutRemoveBricksTask, 2)))); + prepareMocks(cmd); + assertFalse(cmd.canDoAction()); + } + + @Test + public void canDoActionFailesOnVolumeWithRemoveBricksTaskNotFinished() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithRemoveBricksTaskNotFinished, + getBricks(volumeWithRemoveBricksTaskNotFinished, 2)))); + prepareMocks(cmd); + assertFalse(cmd.canDoAction()); + } + + @Test + public void canDoActionFailsOnNull() { + cmd = + spy(new CommitRemoveGlusterVolumeBricksCommand(new GlusterVolumeRemoveBricksParameters(volumeWithRemoveBricksTaskNull, + getBricks(volumeWithRemoveBricksTaskNull, 2)))); + prepareMocks(cmd); + assertFalse(cmd.canDoAction()); + } +} 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 ea83029..182a364 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 @@ -286,6 +286,8 @@ GLUSTER_VOLUME_REBALANCE_STOP_FAILED(4079), GLUSTER_VOLUME_REMOVE_BRICKS_STOPPED(4080), GLUSTER_VOLUME_REMOVE_BRICKS_STOP_FAILED(4081), + GLUSTER_VOLUME_REMOVE_BRICKS_COMMITED(4082), + GLUSTER_VOLUME_REMOVE_BRICKS_COMMIT_FAILED(4083), USER_FORCE_SELECTED_SPM(159), USER_VDS_RESTART(41), diff --git a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllErrors.java b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllErrors.java index e9de9c3..ea0c163 100644 --- a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllErrors.java +++ b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/errors/VdcBllErrors.java @@ -362,6 +362,7 @@ GlusterVolumeReplaceBrickStartFailed(4142), GlusterVolumeListFailed(4149), GlusterVolumeRemoveBricksStopFailed(4150), + GlusterVolumeRemoveBricksCommitFailed(4153), GlusterVolumeOptionInfoFailed(4154), GlusterVolumeResetOptionsFailed(4155), GlusterVolumeRemoveBricksFailed(4156), 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 8088233..a66e810 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 @@ -95,6 +95,7 @@ VAR__ACTION__FORCE_SELECT, VAR__ACTION__EXTEND_IMAGE_SIZE, VAR__ACTION__REMOVE_BRICK_STOP, + VAR__ACTION__REMOVE_BRICK_COMMIT, // Host statuses replacements VAR__HOST_STATUS__UP, @@ -719,6 +720,7 @@ ACTION_TYPE_FAILED_GLUSTER_VOLUME_IS_DOWN(ErrorType.CONFLICT), ACTION_TYPE_FAILED_NOT_A_GLUSTER_VOLUME_BRICK(ErrorType.BAD_PARAMETERS), ACTION_TYPE_FAILED_GLUSTER_VOLUME_REMOVE_BRICK_NOT_STARTED(ErrorType.CONFLICT), + ACTION_TYPE_FAILED_GLUSTER_VOLUME_REMOVE_BRICK_NOT_FINISHED(ErrorType.CONFLICT), ACTION_TYPE_FAILED_CAN_NOT_REMOVE_ALL_BRICKS_FROM_VOLUME(ErrorType.CONFLICT), ACTION_TYPE_FAILED_CAN_NOT_REDUCE_REPLICA_COUNT_MORE_THAN_ONE(ErrorType.CONFLICT), ACTION_TYPE_FAILED_CAN_NOT_INCREASE_REPLICA_COUNT_MORE_THAN_ONE(ErrorType.CONFLICT), diff --git a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/vdscommands/VDSCommandType.java b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/vdscommands/VDSCommandType.java index 8e1fa2a..bb87f6f 100644 --- a/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/vdscommands/VDSCommandType.java +++ b/backend/manager/modules/common/src/main/java/org/ovirt/engine/core/common/vdscommands/VDSCommandType.java @@ -150,6 +150,7 @@ ManageGlusterService("org.ovirt.engine.core.vdsbroker.gluster"), GetDiskAlignment("org.ovirt.engine.core.vdsbroker.vdsbroker"), StopRemoveGlusterVolumeBricks("org.ovirt.engine.core.vdsbroker.gluster"), + CommitRemoveGlusterVolumeBricks("org.ovirt.engine.core.vdsbroker.gluster"), ; String packageName; -- To view, visit http://gerrit.ovirt.org/19100 To unsubscribe, visit http://gerrit.ovirt.org/settings Gerrit-MessageType: newchange Gerrit-Change-Id: Icbf0e615b067638b56af81e2dabe06512d92d73a Gerrit-PatchSet: 1 Gerrit-Project: ovirt-engine Gerrit-Branch: master Gerrit-Owner: Shubhendu Tripathi <shtri...@redhat.com> _______________________________________________ Engine-patches mailing list Engine-patches@ovirt.org http://lists.ovirt.org/mailman/listinfo/engine-patches