Feature Approval Workflow for rollouts (#678)

* implement feature approval workflow

Signed-off-by: Ioannis Spyropoulos <ioannis.spyropoulos@bosch-si.com>
Signed-off-by: Michael Müller <Michael.Mueller17@bosch-si.com>

* add documentation for REST endpoints

Signed-off-by: Ioannis Spyropoulos <ioannis.spyropoulos@bosch-si.com>
Signed-off-by: Michael Müller <Michael.Mueller17@bosch-si.com>

* fix broken documentation test

Signed-off-by: Ioannis Spyropoulos <ioannis.spyropoulos@bosch-si.com>

* fix broken documentation test II

Signed-off-by: Ioannis Spyropoulos <ioannis.spyropoulos@bosch-si.com>
This commit is contained in:
Michael Müller
2018-06-04 16:36:56 +02:00
committed by Dominic Schabel
parent 8a14c931c8
commit cef7c2bbf2
43 changed files with 1056 additions and 43 deletions

View File

@@ -27,6 +27,7 @@ import org.eclipse.hawkbit.repository.model.Target;
import org.eclipse.hawkbit.repository.model.TargetTag;
import org.eclipse.hawkbit.repository.model.TargetTagAssignmentResult;
import org.eclipse.hawkbit.repository.test.util.AbstractIntegrationTest;
import org.eclipse.hawkbit.repository.test.util.RolloutTestApprovalStrategy;
import org.eclipse.hawkbit.tenancy.configuration.TenantConfigurationProperties;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.SpringApplicationConfiguration;
@@ -95,6 +96,9 @@ public abstract class AbstractJpaIntegrationTest extends AbstractIntegrationTest
@Autowired
protected TenantConfigurationProperties tenantConfigurationProperties;
@Autowired
protected RolloutTestApprovalStrategy approvalStrategy;
@Transactional(readOnly = true)
protected List<Action> findActionsByRolloutAndStatus(final Rollout rollout, final Action.Status actionStatus) {
return Lists.newArrayList(actionRepository.findByRolloutIdAndStatus(PAGE, rollout.getId(), actionStatus));

View File

@@ -68,12 +68,17 @@ import org.eclipse.hawkbit.repository.model.TotalTargetCountStatus;
import org.eclipse.hawkbit.repository.test.matcher.Expect;
import org.eclipse.hawkbit.repository.test.matcher.ExpectEvents;
import org.eclipse.hawkbit.tenancy.configuration.TenantConfigurationProperties.TenantConfigurationKey;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Slice;
import org.springframework.data.domain.Sort;
import org.springframework.data.domain.Sort.Direction;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
import ru.yandex.qatools.allure.annotations.Description;
import ru.yandex.qatools.allure.annotations.Features;
import ru.yandex.qatools.allure.annotations.Step;
@@ -87,6 +92,12 @@ import ru.yandex.qatools.allure.annotations.Title;
@Stories("Rollout Management")
public class RolloutManagementTest extends AbstractJpaIntegrationTest {
@Before
@After
public void reset() {
this.approvalStrategy.setApprovalNeeded(false);
}
@Test
@Description("Verifies that a running action with distribution-set (A) is not canceled by a rollout which tries to also assign a distribution-set (A)")
public void rolloutShouldNotCancelRunningActionWithTheSameDistributionSet() {
@@ -1539,6 +1550,59 @@ public class RolloutManagementTest extends AbstractJpaIntegrationTest {
}
@Test
@Description("Creating a rollout with approval role or approval engine disabled results in the rollout being in " +
"READY state.")
public void createdRolloutWithApprovalRoleOrApprovalDisabledTransitionsToReadyState() {
approvalStrategy.setApprovalNeeded(false);
final String successCondition = "50";
final String errorCondition = "80";
final Rollout rollout = createSimpleTestRolloutWithTargetsAndDistributionSet(10, 10,
5, successCondition, errorCondition);
assertThat(rollout.getStatus()).isEqualTo(Rollout.RolloutStatus.READY);
}
@Test
@Description("Creating a rollout without approver role and approval enabled leads to transition to " +
"WAITING_FOR_APPROVAL state.")
public void createdRolloutWithoutApprovalRoleTransitionsToWaitingForApprovalState() {
approvalStrategy.setApprovalNeeded(true);
final String successCondition = "50";
final String errorCondition = "80";
final Rollout rollout = createSimpleTestRolloutWithTargetsAndDistributionSet(10, 10,
5, successCondition, errorCondition);
assertThat(rollout.getStatus()).isEqualTo(Rollout.RolloutStatus.WAITING_FOR_APPROVAL);
}
@Test
@Description("Approving a rollout leads to transition to READY state.")
public void approvedRolloutTransitionsToReadyState() {
approvalStrategy.setApprovalNeeded(true);
final String successCondition = "50";
final String errorCondition = "80";
final Rollout rollout = createSimpleTestRolloutWithTargetsAndDistributionSet(10, 10,
5, successCondition, errorCondition);
assertThat(rollout.getStatus()).isEqualTo(Rollout.RolloutStatus.WAITING_FOR_APPROVAL);
rolloutManagement.approveOrDeny(rollout.getId(), Rollout.ApprovalDecision.APPROVED);
final Rollout resultingRollout = rolloutRepository.findOne(rollout.getId());
assertThat(resultingRollout.getStatus()).isEqualTo(Rollout.RolloutStatus.READY);
}
@Test
@Description("Denying approval for a rollout leads to transition to APPROVAL_DENIED state.")
public void deniedRolloutTransitionsToApprovalDeniedState() {
approvalStrategy.setApprovalNeeded(true);
final String successCondition = "50";
final String errorCondition = "80";
final Rollout rollout = createSimpleTestRolloutWithTargetsAndDistributionSet(10, 10,
5, successCondition, errorCondition);
assertThat(rollout.getStatus()).isEqualTo(Rollout.RolloutStatus.WAITING_FOR_APPROVAL);
rolloutManagement.approveOrDeny(rollout.getId(), Rollout.ApprovalDecision.DENIED);
final Rollout resultingRollout = rolloutRepository.findOne(rollout.getId());
assertThat(resultingRollout.getStatus()).isEqualTo(RolloutStatus.APPROVAL_DENIED);
}
@Test
@ExpectEvents({ @Expect(type = RolloutDeletedEvent.class, count = 1),
@Expect(type = DistributionSetCreatedEvent.class, count = 1),