/* Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.flowable.cmmn.test.runtime;

import static org.assertj.core.api.Assertions.assertThat;
import static org.flowable.cmmn.api.runtime.PlanItemInstanceState.ACTIVE;
import static org.junit.Assert.assertEquals;

import java.util.List;

import org.flowable.cmmn.api.history.HistoricCaseInstance;
import org.flowable.cmmn.api.runtime.CaseInstance;
import org.flowable.cmmn.api.runtime.CaseInstanceState;
import org.flowable.cmmn.api.runtime.PlanItemInstance;
import org.flowable.cmmn.engine.test.CmmnDeployment;
import org.flowable.cmmn.engine.test.FlowableCmmnTestCase;
import org.flowable.common.engine.api.constant.ReferenceTypes;
import org.junit.Test;

/**
 * Tests that a case task is being completed if its referenced case gets manually termianted through the API, rather than an exit sentry.
 *
 * @author Micha Kiener
 */
public class CompleteCaseTaskByManualTerminationTest extends FlowableCmmnTestCase {

    @Test
    @CmmnDeployment(resources = {
            "org/flowable/cmmn/test/event/CaseInstanceEventsTest.testSimpleSubCase.cmmn",
            "org/flowable/cmmn/test/one-human-task-model.cmmn"
    })
    public void completeCaseTaskOnManualTerminationOfReferencedCaseTest() {
        CaseInstance caseInstance = cmmnRuntimeService.createCaseInstanceBuilder()
            .caseDefinitionKey("mainCase")
            .businessKey("main key")
            .name("name")
            .transientVariable("childBusinessKey", "child key")
            .start();

        List<PlanItemInstance> planItemInstances = getPlanItemInstances(caseInstance.getId());
        assertThat(planItemInstances).extracting(PlanItemInstance::getName).containsExactly("Case Task");
        assertThat(planItemInstances).extracting(PlanItemInstance::getState).containsExactly(ACTIVE);
        assertThat(planItemInstances).extracting(PlanItemInstance::getReferenceType).containsExactly(ReferenceTypes.PLAN_ITEM_CHILD_CASE);
        String childCaseId = planItemInstances.get(0).getReferenceId();

        // manually terminate the case through the API which must also complete the case task and hence complete the root case and end it
        cmmnRuntimeService.terminateCaseInstance(childCaseId);

        HistoricCaseInstance historicCaseInstance = cmmnHistoryService.createHistoricCaseInstanceQuery().caseInstanceId(childCaseId).singleResult();
        assertEquals(historicCaseInstance.getState(), CaseInstanceState.TERMINATED);

        assertCaseInstanceEnded(childCaseId);
        assertCaseInstanceEnded(caseInstance.getId());
    }

    @Test
    @CmmnDeployment(resources = {
            "org/flowable/cmmn/test/event/CaseInstanceEventsTest.testSimpleSubCase.cmmn",
            "org/flowable/cmmn/test/one-human-task-model.cmmn"
    })
    public void completeCaseTaskOnManualTriggerTest() {
        CaseInstance caseInstance = cmmnRuntimeService.createCaseInstanceBuilder()
            .caseDefinitionKey("mainCase")
            .businessKey("main key")
            .name("name")
            .transientVariable("childBusinessKey", "child key")
            .start();

        List<PlanItemInstance> planItemInstances = getPlanItemInstances(caseInstance.getId());
        assertThat(planItemInstances).extracting(PlanItemInstance::getName).containsExactly("Case Task");
        assertThat(planItemInstances).extracting(PlanItemInstance::getState).containsExactly(ACTIVE);
        assertThat(planItemInstances).extracting(PlanItemInstance::getReferenceType).containsExactly(ReferenceTypes.PLAN_ITEM_CHILD_CASE);
        String childCaseId = planItemInstances.get(0).getReferenceId();

        // manually terminate the case through the API which must also complete the case task and hence complete the root case and end it
        cmmnRuntimeService.triggerPlanItemInstance(getPlanItemInstanceIdByName(planItemInstances, "Case Task"));

        HistoricCaseInstance historicCaseInstance = cmmnHistoryService.createHistoricCaseInstanceQuery().caseInstanceId(childCaseId).singleResult();
        assertEquals(historicCaseInstance.getState(), CaseInstanceState.TERMINATED);

        assertCaseInstanceEnded(childCaseId);
        assertCaseInstanceEnded(caseInstance.getId());
    }

    @Test
    @CmmnDeployment(resources = {
            "org/flowable/cmmn/test/event/CaseInstanceEventsTest.testSimpleSubCase.cmmn",
            "org/flowable/cmmn/test/one-human-task-model.cmmn"
    })
    public void completeCaseTaskByCompletingChildCase() {
        CaseInstance caseInstance = cmmnRuntimeService.createCaseInstanceBuilder()
            .caseDefinitionKey("mainCase")
            .businessKey("main key")
            .name("name")
            .transientVariable("childBusinessKey", "child key")
            .start();

        List<PlanItemInstance> planItemInstances = getPlanItemInstances(caseInstance.getId());
        assertThat(planItemInstances).extracting(PlanItemInstance::getName).containsExactly("Case Task");
        assertThat(planItemInstances).extracting(PlanItemInstance::getState).containsExactly(ACTIVE);
        assertThat(planItemInstances).extracting(PlanItemInstance::getReferenceType).containsExactly(ReferenceTypes.PLAN_ITEM_CHILD_CASE);
        String childCaseId = planItemInstances.get(0).getReferenceId();

        planItemInstances = getPlanItemInstances(childCaseId);
        assertThat(planItemInstances).hasSize(1);
        assertPlanItemInstanceState(planItemInstances, "The Task", ACTIVE);
        cmmnRuntimeService.triggerPlanItemInstance(getPlanItemInstanceIdByName(planItemInstances, "The Task"));

        HistoricCaseInstance historicCaseInstance = cmmnHistoryService.createHistoricCaseInstanceQuery().caseInstanceId(childCaseId).singleResult();
        assertEquals(historicCaseInstance.getState(), CaseInstanceState.COMPLETED);

        assertCaseInstanceEnded(childCaseId);
        assertCaseInstanceEnded(caseInstance.getId());
    }
}

@@ -729,53 +729,8 @@
 IVE;
-%0Aimport static org.junit.Assert.assertEquals;
 %0A%0Aim
@@ -2857,38 +2857,36 @@
 ;%0A        assert
-Equals
+That
 (historicCaseIns
@@ -2893,34 +2893,44 @@
 tance.getState()
-, 
+).isEqualTo(
 CaseInstanceStat
@@ -4511,38 +4511,36 @@
 ;%0A        assert
-Equals
+That
 (historicCaseIns
@@ -4547,34 +4547,44 @@
 tance.getState()
-, 
+).isEqualTo(
 CaseInstanceStat
@@ -6229,14 +6229,12 @@
 sert
-Equals
+That
 (his
@@ -6261,18 +6261,28 @@
 tState()
-, 
+).isEqualTo(
 CaseInst

use only one test framework (#3260)