Search in sources :

Example 1 with AcceptResult

use of com.sequenceiq.cloudbreak.common.event.AcceptResult in project cloudbreak by hortonworks.

the class Flow2Handler method handleFlowConflict.

private AcceptResult handleFlowConflict(String key, Payload payload, String flowChainId, Set<FlowLogIdWithTypeAndTimestamp> flowLogItems) {
    AcceptResult acceptResult = null;
    Optional<FlowLog> initFlowLog = flowLogService.findAllByFlowIdOrderByCreatedDesc(flowLogItems.iterator().next().getFlowId()).stream().min(Comparator.comparing(FlowLog::getCreated));
    if (initFlowLog.isPresent()) {
        LOGGER.info("Found previous init flow log: {}", initFlowLog.get());
        if (NullUtil.allNotNull(initFlowLog.get().getFlowChainId(), flowChainId)) {
            Optional<Pair<String, Payload>> previousTrigger = flowChains.getRootTriggerEvent(initFlowLog.get().getFlowChainId());
            Optional<Pair<String, Payload>> currentTrigger = flowChains.getRootTriggerEvent(flowChainId);
            if (previousTrigger.isPresent() && currentTrigger.isPresent()) {
                if (isIdempotentTriggers(previousTrigger.get().getRight(), currentTrigger.get().getRight())) {
                    LOGGER.info("Idempotent flow chain trigger. Running {}, requested {}", previousTrigger, currentTrigger);
                    acceptResult = FlowAcceptResult.runningInFlowChain(previousTrigger.get().getLeft());
                }
            }
        } else if (NullUtil.allNull(initFlowLog.get().getFlowChainId(), flowChainId)) {
            Payload previousTrigger = FlowLogUtil.tryDeserializePayload(initFlowLog.get());
            if (isIdempotentTriggers(previousTrigger, payload)) {
                LOGGER.info("Idempotent flow trigger. Running {}, requested {}", previousTrigger, payload);
                acceptResult = FlowAcceptResult.runningInFlow(initFlowLog.get().getFlowId());
            }
        }
    }
    if (acceptResult == null) {
        LOGGER.info("Flow operation not allowed, other flow is running. Resource ID {}, event {}", payload.getResourceId(), key);
        acceptResult = FlowAcceptResult.alreadyExistingFlow(flowLogItems);
    }
    flowChains.removeFullFlowChain(flowChainId, false);
    return acceptResult;
}
Also used : FlowLog(com.sequenceiq.flow.domain.FlowLog) Payload(com.sequenceiq.cloudbreak.common.event.Payload) AcceptResult(com.sequenceiq.cloudbreak.common.event.AcceptResult) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) Pair(org.apache.commons.lang3.tuple.Pair)

Example 2 with AcceptResult

use of com.sequenceiq.cloudbreak.common.event.AcceptResult in project cloudbreak by hortonworks.

the class Flow2Handler method doAccept.

private void doAccept(Event<? extends Payload> event, String key, Payload payload, String flowChainId, String flowChainType, FlowParameters flowParameters) {
    try {
        if (FLOW_CANCEL.equals(key)) {
            cancelRunningFlows(payload.getResourceId());
        } else if (FLOW_FINAL.equals(key)) {
            finalizeFlow(flowParameters, flowChainId, payload.getResourceId(), getContextParams(event));
        } else if (flowParameters.getFlowId() == null) {
            AcceptResult result = handleNewFlowRequest(key, payload, flowParameters, flowChainId, flowChainType, getContextParams(event));
            LOGGER.info("Create new flow result {}", result);
            if (isAcceptablePayload(payload)) {
                ((Acceptable) payload).accepted().accept(result);
            }
        } else {
            handleFlowControlEvent(key, payload, flowParameters, flowChainId);
        }
    } catch (FlowNotTriggerableException e) {
        LOGGER.error("Failed to handle flow event.", e);
        if (isAcceptablePayload(payload)) {
            ((Acceptable) payload).accepted().onError(e);
        } else {
            throw e;
        }
    } catch (CloudbreakServiceException e) {
        LOGGER.error("Failed to handle flow event.", e);
        throw e;
    } catch (Exception e) {
        LOGGER.error("Failed to handle flow event.", e);
        throw new CloudbreakServiceException(e);
    }
}
Also used : FlowNotTriggerableException(com.sequenceiq.flow.core.exception.FlowNotTriggerableException) CloudbreakServiceException(com.sequenceiq.cloudbreak.common.exception.CloudbreakServiceException) Acceptable(com.sequenceiq.cloudbreak.common.event.Acceptable) AcceptResult(com.sequenceiq.cloudbreak.common.event.AcceptResult) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) TransactionRuntimeExecutionException(com.sequenceiq.cloudbreak.common.service.TransactionService.TransactionRuntimeExecutionException) BadRequestException(javax.ws.rs.BadRequestException) InternalServerErrorException(javax.ws.rs.InternalServerErrorException) TransactionExecutionException(com.sequenceiq.cloudbreak.common.service.TransactionService.TransactionExecutionException) FlowNotFoundException(com.sequenceiq.flow.core.exception.FlowNotFoundException) FlowNotTriggerableException(com.sequenceiq.flow.core.exception.FlowNotTriggerableException) CloudbreakServiceException(com.sequenceiq.cloudbreak.common.exception.CloudbreakServiceException)

Example 3 with AcceptResult

use of com.sequenceiq.cloudbreak.common.event.AcceptResult in project cloudbreak by hortonworks.

the class EventSender method doSend.

private FlowIdentifier doSend(BaseFlowEvent event, Event.Headers headers, String resourceName) {
    Event<BaseFlowEvent> eventWithErrHandler = eventFactory.createEventWithErrHandler(new HashMap<>(headers.asMap()), event);
    reactor.notify(event.selector(), eventWithErrHandler);
    Promise<AcceptResult> accepted = eventWithErrHandler.getData().accepted();
    String resourceCrn = event.getResourceCrn();
    if (accepted != null) {
        try {
            FlowAcceptResult acceptResult = (FlowAcceptResult) accepted.await(TIMEOUT, TimeUnit.SECONDS);
            return createFlowIdentifier(acceptResult, resourceCrn);
        } catch (InterruptedException e) {
            throw new IllegalStateException(e.getMessage());
        }
    }
    if (headers.contains(FLOW_ID)) {
        return new FlowIdentifier(FlowType.FLOW, headers.get(FLOW_ID));
    } else if (headers.contains(FLOW_CHAIN_ID)) {
        return new FlowIdentifier(FlowType.FLOW_CHAIN, headers.get(FLOW_CHAIN_ID));
    }
    LOGGER.error("Accepted is null, header does not contains flow or flow chain id, event: {}, header: {}", event, headers);
    reactorReporter.logErrorReport();
    throw new FlowNotAcceptedException(String.format("Timeout happened when trying to start the flow for stack %s.", resourceCrn));
}
Also used : FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) FlowIdentifier(com.sequenceiq.flow.api.model.FlowIdentifier) AcceptResult(com.sequenceiq.cloudbreak.common.event.AcceptResult) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) FlowNotAcceptedException(com.sequenceiq.cloudbreak.exception.FlowNotAcceptedException)

Example 4 with AcceptResult

use of com.sequenceiq.cloudbreak.common.event.AcceptResult in project cloudbreak by hortonworks.

the class FlowComponentTest method startNestedFlowChainThenWaitForComplete.

@Test
public void startNestedFlowChainThenWaitForComplete() throws InterruptedException {
    long resourceId = RESOURCE_ID_SEC.incrementAndGet();
    Promise<AcceptResult> accepted1 = new Promise<>();
    SleepChainTriggerEvent sleepChainTriggerEvent1 = new SleepChainTriggerEvent(resourceId, Lists.newArrayList(new SleepConfig(SLEEP_TIME, SleepStartEvent.NEVER_FAIL)), accepted1);
    SleepChainTriggerEvent sleepChainTriggerEvent2 = new SleepChainTriggerEvent(resourceId, Lists.newArrayList(new SleepConfig(SLEEP_TIME, SleepStartEvent.NEVER_FAIL)), accepted1);
    NestedSleepChainTriggerEvent nestedSleepChainTriggerEvent1 = new NestedSleepChainTriggerEvent(resourceId, Lists.newArrayList(sleepChainTriggerEvent1, sleepChainTriggerEvent2), accepted1);
    Promise<AcceptResult> accepted2 = new Promise<>();
    SleepChainTriggerEvent sleepChainTriggerEvent3 = new SleepChainTriggerEvent(resourceId, Lists.newArrayList(new SleepConfig(SLEEP_TIME, SleepStartEvent.NEVER_FAIL)), accepted2);
    SleepChainTriggerEvent sleepChainTriggerEvent4 = new SleepChainTriggerEvent(resourceId, Lists.newArrayList(new SleepConfig(SLEEP_TIME, SleepStartEvent.NEVER_FAIL)), accepted2);
    NestedSleepChainTriggerEvent nestedSleepChainTriggerEvent2 = new NestedSleepChainTriggerEvent(resourceId, Lists.newArrayList(sleepChainTriggerEvent3, sleepChainTriggerEvent4), accepted2);
    FlowAcceptResult acceptResult1 = startNestedSleepFlowChain(nestedSleepChainTriggerEvent1);
    FlowAcceptResult acceptResult2 = startNestedSleepFlowChain(nestedSleepChainTriggerEvent2);
    assertRunningInFlowChain(acceptResult1);
    assertRunningInFlowChain(acceptResult2);
    waitFlowChainToComplete(SLEEP_TIME.multipliedBy(WAIT_FACTOR), acceptResult1);
}
Also used : Promise(reactor.rx.Promise) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) NestedSleepChainTriggerEvent(com.sequenceiq.flow.component.sleep.event.NestedSleepChainTriggerEvent) SleepChainTriggerEvent(com.sequenceiq.flow.component.sleep.event.SleepChainTriggerEvent) NestedSleepChainTriggerEvent(com.sequenceiq.flow.component.sleep.event.NestedSleepChainTriggerEvent) AcceptResult(com.sequenceiq.cloudbreak.common.event.AcceptResult) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) SleepConfig(com.sequenceiq.flow.component.sleep.event.SleepConfig) Test(org.junit.jupiter.api.Test) SpringBootTest(org.springframework.boot.test.context.SpringBootTest)

Example 5 with AcceptResult

use of com.sequenceiq.cloudbreak.common.event.AcceptResult in project cloudbreak by hortonworks.

the class ReactorNotifierTest method testAcceptedReturnNull.

@Test(expected = FlowNotAcceptedException.class)
public void testAcceptedReturnNull() throws InterruptedException {
    Stack stack = TestUtil.stack();
    stack.setCluster(TestUtil.cluster());
    when(stackService.getByIdWithTransaction(1L)).thenReturn(stack);
    Acceptable data = mock(Acceptable.class);
    Promise<AcceptResult> accepted = (Promise<AcceptResult>) mock(Promise.class);
    when(data.accepted()).thenReturn(accepted);
    when(data.getResourceId()).thenReturn(1L);
    Event<Acceptable> event = new Event<>(data);
    when(eventFactory.createEventWithErrHandler(anyMap(), any(Acceptable.class))).thenReturn(event);
    when(accepted.await(10L, TimeUnit.SECONDS)).thenReturn(null);
    underTest.notify(1L, "RANDOM", data, stackService::getByIdWithTransaction);
    verify(reactorReporter, times(1)).logInfoReport();
    verify(reactorReporter, times(1)).logErrorReport();
    verify(reactor, times(1)).notify(eq("RANDOM"), eq(event));
    verify(accepted, times(1)).await(10L, TimeUnit.SECONDS);
}
Also used : Promise(reactor.rx.Promise) Acceptable(com.sequenceiq.cloudbreak.common.event.Acceptable) Event(reactor.bus.Event) BaseFlowEvent(com.sequenceiq.flow.reactor.api.event.BaseFlowEvent) AcceptResult(com.sequenceiq.cloudbreak.common.event.AcceptResult) FlowAcceptResult(com.sequenceiq.flow.core.model.FlowAcceptResult) Stack(com.sequenceiq.cloudbreak.domain.stack.Stack) Test(org.junit.Test)

Aggregations

AcceptResult (com.sequenceiq.cloudbreak.common.event.AcceptResult)8 FlowAcceptResult (com.sequenceiq.flow.core.model.FlowAcceptResult)8 Acceptable (com.sequenceiq.cloudbreak.common.event.Acceptable)4 Promise (reactor.rx.Promise)4 Stack (com.sequenceiq.cloudbreak.domain.stack.Stack)3 BaseFlowEvent (com.sequenceiq.flow.reactor.api.event.BaseFlowEvent)3 Test (org.junit.Test)3 Event (reactor.bus.Event)3 FlowIdentifier (com.sequenceiq.flow.api.model.FlowIdentifier)2 DetailedStackStatus (com.sequenceiq.cloudbreak.api.endpoint.v4.common.DetailedStackStatus)1 Payload (com.sequenceiq.cloudbreak.common.event.Payload)1 CloudbreakServiceException (com.sequenceiq.cloudbreak.common.exception.CloudbreakServiceException)1 TransactionExecutionException (com.sequenceiq.cloudbreak.common.service.TransactionService.TransactionExecutionException)1 TransactionRuntimeExecutionException (com.sequenceiq.cloudbreak.common.service.TransactionService.TransactionRuntimeExecutionException)1 StackStatus (com.sequenceiq.cloudbreak.domain.stack.StackStatus)1 FlowNotAcceptedException (com.sequenceiq.cloudbreak.exception.FlowNotAcceptedException)1 FlowsAlreadyRunningException (com.sequenceiq.cloudbreak.exception.FlowsAlreadyRunningException)1 NestedSleepChainTriggerEvent (com.sequenceiq.flow.component.sleep.event.NestedSleepChainTriggerEvent)1 SleepChainTriggerEvent (com.sequenceiq.flow.component.sleep.event.SleepChainTriggerEvent)1 SleepConfig (com.sequenceiq.flow.component.sleep.event.SleepConfig)1