#
#    Copyright (c) 2024 Project CHIP Authors
#    All rights reserved.
#
#    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.
#

import json
import logging
import queue
import time
from dataclasses import dataclass
from typing import Any

import chip.clusters as Clusters
import psutil
from chip.clusters import ClusterObjects as ClusterObjects
from chip.clusters.Attribute import EventReadResult, SubscriptionTransaction
from chip.clusters.Types import NullValue
from chip.interaction_model import InteractionModelError, Status
from matter_testing_support import EventChangeCallback, TestStep
from mobly import asserts


def get_pid(name):
    pid = None

    for proc in psutil.process_iter():
        if name in proc.name():
            pid = proc.pid
            break

    return pid


@dataclass
class TestInfo:
    pics_code: str
    cluster: Clusters


class EventSpecificChangeCallback:
    def __init__(self, expected_event: ClusterObjects.ClusterEvent):
        """This class creates a queue to store received event callbacks, that can be checked by the test script
           expected_event: is the expected event
        """
        self._q = queue.Queue()
        self._expected_cluster_id = expected_event.cluster_id
        self._expected_event = expected_event

    async def start(self, dev_ctrl, node_id: int, endpoint: int):
        """This starts a subscription for events on the specified node_id and endpoint. The event is specified when the class instance is created."""
        self._subscription = await dev_ctrl.ReadEvent(node_id,
                                                      events=[(endpoint, self._expected_event, True)], reportInterval=(1, 5),
                                                      fabricFiltered=False, keepSubscriptions=True, autoResubscribe=False)
        self._subscription.SetEventUpdateCallback(self.__call__)

    def __call__(self, res: EventReadResult, transaction: SubscriptionTransaction):
        """This is the subscription callback when an event is received.
           It checks the if the event is the expected one and then posts it into the queue for later processing."""
        if res.Status == Status.Success and res.Header.ClusterId == self._expected_cluster_id and res.Header.EventId == self._expected_event.event_id:
            logging.info(
                f'Got subscription report for event {self._expected_event.event_id} on cluster {self._expected_cluster_id}: {res.Data}')
            self._q.put(res)

    def wait_for_event_report(self, timeout: int = 10):
        """This function allows a test script to block waiting for the specific event to arrive with a timeout.
           It returns the event data so that the values can be checked."""
        try:
            res = self._q.get(block=True, timeout=timeout)
        except queue.Empty:
            asserts.fail(f"Failed to receive a report for the event {self._expected_event}")

        asserts.assert_equal(res.Header.ClusterId, self._expected_cluster_id, "Expected cluster ID not found in event report")
        asserts.assert_equal(res.Header.EventId, self._expected_event.event_id, "Expected event ID not found in event report")
        return res.Data


class TC_OPSTATE_BASE():
    def setup_base(self, test_info=None, app_pipe="/tmp/chip_all_clusters_fifo_"):

        asserts.assert_true(test_info is not None,
                            "You shall define the test info!")

        self.test_info = test_info
        self.app_pipe = app_pipe

        if self.test_info.cluster == Clusters.OperationalState:
            self.device = "Generic"
        elif self.test_info.cluster == Clusters.OvenCavityOperationalState:
            self.device = "Oven"
        else:
            asserts.fail(f"This provided cluster ({self.test_info.cluster}) is not supported!")

    def init_test(self):
        self.is_ci = self.check_pics("PICS_SDK_CI_ONLY")
        if self.is_ci:
            app_pid = self.matter_test_config.app_pid
            if app_pid == 0:
                app_pid = get_pid("chip-all-clusters-app")
                if app_pid is None:
                    asserts.fail("The --app-pid flag must be set when PICS_SDK_CI_ONLY is set")
            self.app_pipe = self.app_pipe + str(app_pid)

    # Sends and out-of-band command to test-app
    def write_to_app_pipe(self, command):
        with open(self.app_pipe, "w") as app_pipe:
            app_pipe.write(command + "\n")

    def send_raw_manual_or_pipe_command(self, command):
        if self.is_ci:
            self.write_to_app_pipe(command)
            time.sleep(0.1)
        else:
            input("Press Enter when done.\n")

    def send_manual_or_pipe_command(self, device: str, name: str, operation: str, param: Any = None):
        command = {
            "Name": name,
            "Device": device,
            "Operation": operation,
        }

        if param is not None:
            command["Param"] = param

        self.send_raw_manual_or_pipe_command(json.dumps(command))

    async def send_cmd(self, endpoint, cmd, timedRequestTimeoutMs=None):
        logging.info(f"##### Command {cmd}")

        try:
            return await self.send_single_cmd(cmd=cmd,
                                              endpoint=endpoint,
                                              timedRequestTimeoutMs=timedRequestTimeoutMs)

        except InteractionModelError as e:
            asserts.fail(f"Unexpected error returned: {e.status}")

    async def send_cmd_expect_response(self, endpoint, cmd, expected_response, timedRequestTimeoutMs=None):
        ret = await self.send_cmd(endpoint=endpoint,
                                  cmd=cmd,
                                  timedRequestTimeoutMs=timedRequestTimeoutMs)

        asserts.assert_equal(ret.commandResponseState.errorStateID,
                             expected_response,
                             f"Command response ({ret.commandResponseState}) mismatched from expectation for {cmd} on {endpoint}")

    async def read_expect_success(self, endpoint, attribute):
        logging.info(f"##### Read {attribute}")
        attr_value = await self.read_single_attribute_check_success(endpoint=endpoint,
                                                                    cluster=self.test_info.cluster,
                                                                    attribute=attribute)
        logging.info(f"## {attribute}: {attr_value}")

        return attr_value

    async def read_and_expect_value(self, endpoint, attribute, expected_value):
        attr_value = await self.read_expect_success(
            endpoint=endpoint,
            attribute=attribute)

        asserts.assert_equal(attr_value, expected_value,
                             f"Value mismatched from expectation for {attribute} on {endpoint}")

    async def read_and_expect_property_value(self, endpoint, attribute, attr_property, expected_value):
        attr_value = await self.read_expect_success(
            endpoint=endpoint,
            attribute=attribute)
        field_value = getattr(attr_value, attr_property)

        asserts.assert_equal(field_value, expected_value,
                             f"Property '{attr_property}' value mismatched from expectation for {attribute} on {endpoint}")

    async def read_and_expect_array_contains(self, endpoint, attribute, expected_contains):
        attr_value = await self.read_expect_success(
            endpoint=endpoint,
            attribute=attribute)
        attr_value.sort()
        expected_contains.sort()

        logging.info("## Current value: [%s]" % attr_value)
        logging.info("## Expected value: [%s]" % expected_contains)

        for item in expected_contains:
            if item not in attr_value:
                asserts.fail("Entry (%s), not found! The returned value SHALL include all the entries: [%s]!" % (
                    item, expected_contains))

    ############################
    #   TEST CASE 1.1
    ############################
    def STEPS_TC_OPSTATE_BASE_1_1(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "TH reads from the DUT the ClusterRevision attribute"),
                 TestStep(3, "TH reads from the DUT the FeatureMap attribute"),
                 TestStep(4, "TH reads from the DUT the AttributeList attribute"),
                 TestStep(5, "TH reads from the DUT the EventList attribute"),
                 TestStep(6, "TH reads from the DUT the AcceptedCommandList attribute"),
                 TestStep(7, "TH reads from the DUT the GeneratedCommandList attribute")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_1_1(self, endpoint=1, cluster_revision=1, feature_map=0):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes
        events = cluster.Events
        commands = cluster.Commands

        self.init_test()

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        # STEP 2: TH reads from the DUT the ClusterRevision attribute
        self.step(2)
        await self.read_and_expect_value(endpoint=endpoint,
                                         attribute=attributes.ClusterRevision,
                                         expected_value=cluster_revision)

        # STEP 3: TH reads from the DUT the FeatureMap attribute
        self.step(3)
        await self.read_and_expect_value(endpoint=endpoint,
                                         attribute=attributes.FeatureMap,
                                         expected_value=feature_map)

        # STEP 4: TH reads from the DUT the AttributeList attribute
        self.step(4)
        expected_value = [
            attributes.PhaseList.attribute_id,
            attributes.CurrentPhase.attribute_id,
            attributes.OperationalStateList.attribute_id,
            attributes.OperationalState.attribute_id,
            attributes.OperationalError.attribute_id,
            attributes.GeneratedCommandList.attribute_id,
            attributes.AcceptedCommandList.attribute_id,
            attributes.AttributeList.attribute_id,
            attributes.FeatureMap.attribute_id,
            attributes.ClusterRevision.attribute_id
        ]

        if self.check_pics(f"{self.test_info.pics_code}.S.A0002"):
            expected_value.append(attributes.CountdownTime.attribute_id)

        await self.read_and_expect_array_contains(endpoint=endpoint,
                                                  attribute=attributes.AttributeList,
                                                  expected_contains=expected_value)

        # STEP 5: TH reads from the DUT the EventList attribute
        self.step(5)
        if self.pics_guard(self.check_pics("PICS_EVENT_LIST_ENABLED")):
            expected_value = [
                events.OperationalError.event_id,
            ]

            if self.check_pics(f"{self.test_info.pics_code}.S.E01"):
                expected_value.append(events.OperationCompletion.event_id)

            await self.read_and_expect_array_contains(endpoint=endpoint,
                                                      attribute=attributes.EventList,
                                                      expected_contains=expected_value)

        # STEP 6: TH reads from the DUT the AcceptedCommandList attribute
        self.step(6)
        expected_value = []

        if (self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp")):
            expected_value.append(commands.Pause.command_id)

        if (self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp")):
            expected_value.append(commands.Stop.command_id)

        if self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp"):
            expected_value.append(commands.Start.command_id)

        if (self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp")):
            expected_value.append(commands.Resume.command_id)

        await self.read_and_expect_array_contains(endpoint=endpoint,
                                                  attribute=attributes.AcceptedCommandList,
                                                  expected_contains=expected_value)

        # STEP 7: TH reads from the DUT the AcceptedCommandList attribute
        self.step(7)
        expected_value = []

        if (self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") or
                self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp")):
            expected_value.append(commands.OperationalCommandResponse.command_id)

        await self.read_and_expect_array_contains(endpoint=endpoint,
                                                  attribute=attributes.GeneratedCommandList,
                                                  expected_contains=expected_value)

    ############################
    #   TEST CASE 2.1
    ############################
    def STEPS_TC_OPSTATE_BASE_2_1(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "TH reads from the DUT the PhaseList attribute"),
                 TestStep(3, "TH reads from the DUT the CurrentPhase attribute"),
                 TestStep(4, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(5, "TH reads from the DUT the OperationalStateList attribute"),
                 TestStep(6, "TH reads from the DUT the OperationalState attribute"),
                 TestStep("6a", "Manually put the device in the Stopped(0x00) operational state"),
                 TestStep("6b", "TH reads from the DUT the OperationalState attribute"),
                 TestStep("6c", "Manually put the device in the Running(0x01) operational state"),
                 TestStep("6d", "TH reads from the DUT the OperationalState attribute"),
                 TestStep("6e", "Manually put the device in the Paused(0x02) operational state"),
                 TestStep("6f", "TH reads from the DUT the OperationalState attribute"),
                 TestStep("6g", "Manually put the device in the Error(0x03) operational state"),
                 TestStep("6h", "TH reads from the DUT the OperationalState attribute"),
                 TestStep(7, "TH reads from the DUT the OperationalError attribute"),
                 TestStep("7a", "Manually put the device in the NoError(0x00) error state"),
                 TestStep("7b", "TH reads from the DUT the OperationalError attribute"),
                 TestStep("7c", "Manually put the device in the UnableToStartOrResume(0x01) error state"),
                 TestStep("7d", "TH reads from the DUT the OperationalError attribute"),
                 TestStep("7e", "Manually put the device in the UnableToCompleteOperation(0x02) error state"),
                 TestStep("7f", "TH reads from the DUT the OperationalError attribute"),
                 TestStep("7g", "Manually put the device in the CommandInvalidInState(0x03) error state"),
                 TestStep("7h", "TH reads from the DUT the OperationalError attribute")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_2_1(self, endpoint=1):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes

        self.init_test()

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        # STEP 2: TH reads from the DUT the PhaseList attribute
        self.step(2)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0000")):
            phase_list = await self.read_expect_success(endpoint=endpoint,
                                                        attribute=attributes.PhaseList)
            if phase_list is not NullValue:
                phase_list_len = len(phase_list)
                asserts.assert_less_equal(phase_list_len, 32,
                                          f"PhaseList length({phase_list_len}) must be less than 32!")

        # STEP 3: TH reads from the DUT the CurrentPhase attribute
        self.step(3)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0001")):
            current_phase = await self.read_expect_success(endpoint=endpoint,
                                                           attribute=attributes.CurrentPhase)
            if (phase_list == NullValue) or (not phase_list):
                asserts.assert_true(current_phase == NullValue, f"CurrentPhase({current_phase}) should be null")
            else:
                asserts.assert_true(0 <= current_phase and current_phase < phase_list_len,
                                    f"CurrentPhase({current_phase}) must be between 0 and {(phase_list_len - 1)}")

        # STEP 4: TH reads from the DUT the CountdownTime attribute
        self.step(4)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                            attribute=attributes.CountdownTime)
            if countdown_time is not NullValue:
                asserts.assert_true(0 <= countdown_time <= 259200,
                                    f"CountdownTime({countdown_time}) must be between 0 and 259200")

        # STEP 5: TH reads from the DUT the OperationalStateList attribute
        self.step(5)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0003")):
            operational_state_list = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.OperationalStateList)
            defined_states = [state.value for state in cluster.Enums.OperationalStateEnum
                              if state != cluster.Enums.OperationalStateEnum.kUnknownEnumValue]

            for state in operational_state_list:
                in_range = (0x80 <= state.operationalStateID <= 0xBF)
                asserts.assert_true(state.operationalStateID in defined_states or in_range,
                                    "Found a OperationalStateList entry with invalid ID value!")
                if in_range:
                    asserts.assert_true(state.operationalStateLabel is not None,
                                        "The OperationalStateLabel should be populated")

                if state.operationalStateID == cluster.Enums.OperationalStateEnum.kError:
                    error_state_present = True

            asserts.assert_true(error_state_present, "The OperationalStateList does not have an ID entry of Error(0x03)")

        # STEP 6: TH reads from the DUT the OperationalState attribute
        self.step(6)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
            operational_state = await self.read_expect_success(endpoint=endpoint,
                                                               attribute=attributes.OperationalState)
            in_range = (0x80 <= operational_state <= 0xBF)
            asserts.assert_true(operational_state in defined_states or in_range,
                                "OperationalState has an invalid ID value!")

            # STEP 6a: Manually put the device in the Stopped(0x00) operational state
            self.step("6a")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ST_STOPPED")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="Stop")
                # STEP 6b: TH reads from the DUT the OperationalState attribute
                self.step("6b")
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kStopped)
            else:
                self.skip_step("6b")

            # STEP 6c: Manually put the device in the Running(0x01) operational state
            self.step("6c")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ST_RUNNING")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="Start")
                # STEP 6d: TH reads from the DUT the OperationalState attribute
                self.step("6d")
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kRunning)
            else:
                self.skip_step("6d")

            # STEP 6e: Manually put the device in the Paused(0x02) operational state
            self.step("6e")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ST_PAUSED")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="Pause")
                # STEP 6f: TH reads from the DUT the OperationalState attribute
                self.step("6f")
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kPaused)
            else:
                self.skip_step("6f")

            # STEP 6g: Manually put the device in the Error(0x03) operational state
            self.step("6g")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ST_ERROR")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="OnFault",
                                                 param=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)
                # STEP 6h: TH reads from the DUT the OperationalState attribute
                self.step("6h")
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kError)
            else:
                self.skip_step("6h")

        # STEP 7: TH reads from the DUT the OperationalError attribute
        self.step(7)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0005")):
            operational_error = await self.read_expect_success(endpoint=endpoint,
                                                               attribute=attributes.OperationalError)
            # Defined Errors
            defined_errors = [error.value for error in cluster.Enums.ErrorStateEnum
                              if error != cluster.Enums.ErrorStateEnum.kUnknownEnumValue]

            in_range = (0x80 <= operational_error.errorStateID <= 0xBF)
            asserts.assert_true(operational_error.errorStateID in defined_errors
                                or in_range, "OperationalError has an invalid ID value!")
            if in_range:
                asserts.assert_true(operational_error.errorStateLabel is not None, "ErrorStateLabel should be populated")

            # STEP 7a: Manually put the device in the NoError(0x00) error state
            self.step("7a")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_NO_ERROR")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="OnFault",
                                                 param=cluster.Enums.ErrorStateEnum.kNoError)
                # STEP 7b: TH reads from the DUT the OperationalError attribute
                self.step("7b")
                await self.read_and_expect_property_value(endpoint=endpoint,
                                                          attribute=attributes.OperationalError,
                                                          attr_property="errorStateID",
                                                          expected_value=cluster.Enums.ErrorStateEnum.kNoError)
            else:
                self.skip_step("7b")

            # STEP 7c: Manually put the device in the UnableToStartOrResume(0x01) error state
            self.step("7c")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_UNABLE_TO_START_OR_RESUME")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="OnFault",
                                                 param=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)
                # STEP 7d: TH reads from the DUT the OperationalError attribute
                self.step("7d")
                await self.read_and_expect_property_value(endpoint=endpoint,
                                                          attribute=attributes.OperationalError,
                                                          attr_property="errorStateID",
                                                          expected_value=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)
            else:
                self.skip_step("7d")

            # STEP 7e: Manually put the device in the UnableToCompleteOperation(0x02) error state
            self.step("7e")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_UNABLE_TO_COMPLETE_OPERATION")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="OnFault",
                                                 param=cluster.Enums.ErrorStateEnum.kUnableToCompleteOperation)
                # STEP 7f: TH reads from the DUT the OperationalError attribute
                self.step("7f")
                await self.read_and_expect_property_value(endpoint=endpoint,
                                                          attribute=attributes.OperationalError,
                                                          attr_property="errorStateID",
                                                          expected_value=cluster.Enums.ErrorStateEnum.kUnableToCompleteOperation)
            else:
                self.skip_step("7f")

            # STEP 7g: Manually put the device in the CommandInvalidInState(0x03) error state
            self.step("7g")
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_COMMAND_INVALID_IN_STATE")):
                self.send_manual_or_pipe_command(name="OperationalStateChange",
                                                 device=self.device,
                                                 operation="OnFault",
                                                 param=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)
                # STEP 7h: TH reads from the DUT the OperationalError attribute
                self.step("7h")
                await self.read_and_expect_property_value(endpoint=endpoint,
                                                          attribute=attributes.OperationalError,
                                                          attr_property="errorStateID",
                                                          expected_value=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)
            else:
                self.skip_step("7h")

    ############################
    #   TEST CASE 2.2
    ############################
    def STEPS_TC_OPSTATE_BASE_2_2(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "Manually put the DUT into a state wherein it can receive a Start Command"),
                 TestStep(3, "TH reads from the DUT the OperationalStateList attribute"),
                 TestStep(4, "TH sends Start command to the DUT"),
                 TestStep(5, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(6, "TH reads from the DUT the OperationalError attribute"),
                 TestStep(7, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(8, "TH reads from the DUT the PhaseList attribute"),
                 TestStep(9, "TH reads from the DUT the CurrentPhase attribute"),
                 TestStep(10, "TH waits for {PIXIT.WAITTIME.COUNTDOWN}"),
                 TestStep(11, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(12, "TH sends Start command to the DUT"),
                 TestStep(13, "TH sends Stop command to the DUT"),
                 TestStep(14, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(15, "TH sends Stop command to the DUT"),
                 TestStep(16, "Manually put the DUT into a state wherein it cannot receive a Start Command"),
                 TestStep(17, "TH sends Start command to the DUT")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_2_2(self, endpoint=1):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes
        commands = cluster.Commands

        self.init_test()

        asserts.assert_true('PIXIT.WAITTIME.COUNTDOWN' in self.matter_test_config.global_test_params,
                            "PIXIT.WAITTIME.COUNTDOWN must be included on the command line in "
                            "the --int-arg flag as PIXIT.WAITTIME.COUNTDOWN:<wait time>")

        wait_time = self.matter_test_config.global_test_params['PIXIT.WAITTIME.COUNTDOWN']

        if wait_time == 0:
            asserts.fail("PIXIT.WAITTIME.COUNTDOWN shall be higher than 0.")

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        # STEP 2: Manually put the DUT into a state wherein it can receive a Start Command
        self.step(2)
        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="OnFault",
                                         param=cluster.Enums.ErrorStateEnum.kNoError)

        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="Stop")

        # STEP 3: TH reads from the DUT the OperationalStateList attribute
        self.step(3)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0003")):
            operational_state_list = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.OperationalStateList)

            operational_state_list_ids = [op_state.operationalStateID for op_state in operational_state_list]

            defined_states = [state.value for state in cluster.Enums.OperationalStateEnum
                              if state != cluster.Enums.OperationalStateEnum.kUnknownEnumValue]

            for state in defined_states:
                if state not in operational_state_list_ids:
                    asserts.fail(f"The list shall include structs with the following OperationalStateIds: {defined_states}")

        # STEP 4: TH sends Start command to the DUT
        self.step(4)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Start(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 5: TH reads from the DUT the OperationalState attribute
        self.step(5)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
            await self.read_and_expect_value(endpoint=endpoint,
                                             attribute=attributes.OperationalState,
                                             expected_value=cluster.Enums.OperationalStateEnum.kRunning)

        # STEP 6: TH reads from the DUT the OperationalError attribute
        self.step(6)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0005")):
            await self.read_and_expect_property_value(endpoint=endpoint,
                                                      attribute=attributes.OperationalError,
                                                      attr_property="errorStateID",
                                                      expected_value=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 7: TH reads from the DUT the CountdownTime attribute
        self.step(7)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            initial_countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.CountdownTime)
            if initial_countdown_time is not NullValue:
                asserts.assert_true(0 <= initial_countdown_time <= 259200,
                                    f"CountdownTime({initial_countdown_time}) must be between 0 and 259200")

        # STEP 8: TH reads from the DUT the PhaseList attribute
        self.step(8)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0000")):
            phase_list = await self.read_expect_success(endpoint=endpoint,
                                                        attribute=attributes.PhaseList)
            phase_list_len = 0
            if phase_list is not NullValue:
                phase_list_len = len(phase_list)
                asserts.assert_less_equal(phase_list_len, 32,
                                          f"PhaseList length({phase_list_len}) must be less than 32!")

        # STEP 9: TH reads from the DUT the CurrentPhase attribute
        self.step(9)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0001")):
            current_phase = await self.read_expect_success(endpoint=endpoint,
                                                           attribute=attributes.CurrentPhase)
            if (phase_list == NullValue) or (not phase_list):
                asserts.assert_equal(current_phase, NullValue, f"CurrentPhase({current_phase}) should be null")
            else:
                asserts.assert_less_equal(0, current_phase,
                                          f"CurrentPhase({current_phase}) must be greater or equal than 0")
                asserts.assert_less(current_phase < phase_list_len,
                                    f"CurrentPhase({current_phase}) must be less then {(phase_list_len - 1)}")

        # STEP 10: TH waits for {PIXIT.WAITTIME.COUNTDOWN}
        self.step(10)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            time.sleep(wait_time)

        # STEP 11: TH reads from the DUT the CountdownTime attribute
        self.step(11)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                            attribute=attributes.CountdownTime)

            if (countdown_time is not NullValue) and (initial_countdown_time is not NullValue):
                asserts.assert_less_equal(countdown_time, (initial_countdown_time - wait_time),
                                          f"The countdown time shall have decreased at least {wait_time:.1f} since start command")

        # STEP 12: TH sends Start command to the DUT
        self.step(12)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Start(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 13: TH sends Stop command to the DUT
        self.step(13)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Stop(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 14: TH reads from the DUT the OperationalState attribute
        self.step(14)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
            await self.read_and_expect_value(endpoint=endpoint,
                                             attribute=attributes.OperationalState,
                                             expected_value=cluster.Enums.OperationalStateEnum.kStopped)

        # STEP 15: TH sends Stop command to the DUT
        self.step(15)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Stop(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 16: Manually put the DUT into a state wherein it cannot receive a Start Command
        self.step(16)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_UNABLE_TO_START_OR_RESUME")):
            self.send_manual_or_pipe_command(name="OperationalStateChange",
                                             device=self.device,
                                             operation="OnFault",
                                             param=cluster.Enums.ErrorStateEnum.kUnableToCompleteOperation)

        # STEP 17: TH sends Start command to the DUT
        self.step(17)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.M.ERR_UNABLE_TO_START_OR_RESUME") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Start(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)

    ############################
    #   TEST CASE 2.3
    ############################
    def STEPS_TC_OPSTATE_BASE_2_3(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "Manually put the DUT into a state wherein it can receive a Pause Command"),
                 TestStep(3, "TH reads from the DUT the OperationalStateList attribute"),
                 TestStep(4, "TH sends Pause command to the DUT"),
                 TestStep(5, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(6, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(7, "TH waits for {PIXIT.WAITTIME.COUNTDOWN}"),
                 TestStep(8, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(9, "TH sends Pause command to the DUT"),
                 TestStep(10, "TH sends Resume command to the DUT"),
                 TestStep(11, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(12, "TH sends Resume command to the DUT"),
                 TestStep(13, "Manually put the device in the Stopped(0x00) operational state"),
                 TestStep(14, "TH sends Pause command to the DUT"),
                 TestStep(15, "TH sends Resume command to the DUT"),
                 TestStep(16, "Manually put the device in the Error(0x03) operational state"),
                 TestStep(17, "TH sends Pause command to the DUT"),
                 TestStep(18, "TH sends Resume command to the DUT")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_2_3(self, endpoint=1):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes
        commands = cluster.Commands

        self.init_test()

        asserts.assert_true('PIXIT.WAITTIME.COUNTDOWN' in self.matter_test_config.global_test_params,
                            "PIXIT.WAITTIME.COUNTDOWN must be included on the command line in "
                            "the --int-arg flag as PIXIT.WAITTIME.COUNTDOWN:<wait time>")

        wait_time = self.matter_test_config.global_test_params['PIXIT.WAITTIME.COUNTDOWN']

        if wait_time == 0:
            asserts.fail("PIXIT.WAITTIME.COUNTDOWN shall be higher than 0.")

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        # STEP 2: Manually put the DUT into a state wherein it can receive a Pause Command
        self.step(2)
        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="OnFault",
                                         param=cluster.Enums.ErrorStateEnum.kNoError)

        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="Start")

        # STEP 3: TH reads from the DUT the OperationalStateList attribute
        self.step(3)
        if self.pics_guard(self.check_pics((f"{self.test_info.pics_code}.S.A0003"))):
            operational_state_list = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.OperationalStateList)

            operational_state_list_ids = [op_state.operationalStateID for op_state in operational_state_list]

            defined_states = [state.value for state in cluster.Enums.OperationalStateEnum
                              if state != cluster.Enums.OperationalStateEnum.kUnknownEnumValue]

            for state in defined_states:
                if state not in operational_state_list_ids:
                    asserts.fail(f"The list shall include structs with the following OperationalStateIds: {defined_states}")

        # STEP 4: TH sends Pause command to the DUT
        self.step(4)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Pause(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 5: TH reads from the DUT the OperationalState attribute
        self.step(5)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
            await self.read_and_expect_value(endpoint=endpoint,
                                             attribute=attributes.OperationalState,
                                             expected_value=cluster.Enums.OperationalStateEnum.kPaused)

        # STEP 6: TH reads from the DUT the CountdownTime attribute
        self.step(6)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            initial_countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.CountdownTime)
            if initial_countdown_time is not NullValue:
                asserts.assert_true(0 <= initial_countdown_time <= 259200,
                                    f"CountdownTime({initial_countdown_time}) must be between 0 and 259200")

        # STEP 7: TH waits for {PIXIT.WAITTIME.COUNTDOWN}
        self.step(7)
        time.sleep(wait_time)

        # STEP 8: TH reads from the DUT the CountdownTime attribute
        self.step(8)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                            attribute=attributes.CountdownTime)

            if (countdown_time is not NullValue) and (initial_countdown_time is not NullValue):
                asserts.assert_equal(countdown_time, initial_countdown_time,
                                     "The countdown time shall be equal since pause command")

        # STEP 9: TH sends Pause command to the DUT
        self.step(9)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Pause(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 10: TH sends Resume command to the DUT
        self.step(10)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Resume(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 11: TH reads from the DUT the OperationalState attribute
        self.step(11)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
            await self.read_and_expect_value(endpoint=endpoint,
                                             attribute=attributes.OperationalState,
                                             expected_value=cluster.Enums.OperationalStateEnum.kRunning)

        # STEP 12: TH sends Resume command to the DUT
        self.step(12)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Resume(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 13: Manually put the device in the Stopped(0x00) operational state
        self.step(13)
        if self.pics_guard(self.check_pics((f"{self.test_info.pics_code}.S.M.ST_STOPPED"))):
            self.send_manual_or_pipe_command(name="OperationalStateChange",
                                             device=self.device,
                                             operation="Stop")

        # STEP 14: TH sends Pause command to the DUT
        self.step(14)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Pause(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)

        # STEP 15: TH sends Resume command to the DUT
        self.step(15)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Resume(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)

        # STEP 16: Manually put the device in the Error(0x03) operational state
        self.step(16)
        if self.pics_guard(self.check_pics((f"{self.test_info.pics_code}.S.M.ST_ERROR"))):
            self.send_manual_or_pipe_command(name="OperationalStateChange",
                                             device=self.device,
                                             operation="OnFault",
                                             param=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)

        # STEP 17: TH sends Pause command to the DUT
        self.step(17)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Pause(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)

        # STEP 18: TH sends Resume command to the DUT
        self.step(18)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Resume(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kCommandInvalidInState)

    ############################
    #   TEST CASE 2.4
    ############################
    def STEPS_TC_OPSTATE_BASE_2_4(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "Set up a subscription to the OperationalError event"),
                 TestStep(3, "At the DUT take the vendor defined action to generate an OperationalError event"),
                 TestStep(4, "TH reads from the DUT the OperationalState attribute")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_2_4(self, endpoint=1):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes
        events = cluster.Events

        self.init_test()

        pixit_var_name = f'PIXIT.{self.test_info.pics_code}.ErrorEventGen'
        print(pixit_var_name in self.matter_test_config.global_test_params)
        asserts.assert_true(pixit_var_name in self.matter_test_config.global_test_params,
                            f"{pixit_var_name} must be included on the command line in the --int-arg flag as {pixit_var_name}:<0 or 1>")

        error_event_gen = self.matter_test_config.global_test_params[pixit_var_name]

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        if self.pics_guard(error_event_gen):
            # STEP 2: Set up a subscription to the OperationalError event
            self.step(2)
            # Subscribe to Events and when they are sent push them to a queue for checking later
            events_callback = EventChangeCallback(cluster)
            await events_callback.start(self.default_controller,
                                        self.dut_node_id,
                                        endpoint)

            # STEP 3: At the DUT take the vendor defined action to generate an OperationalError event
            self.step(3)
            self.send_manual_or_pipe_command(name="OperationalStateChange",
                                             device=self.device,
                                             operation="OnFault",
                                             param=cluster.Enums.ErrorStateEnum.kUnableToStartOrResume)
            event_data = events_callback.wait_for_event_report(events.OperationalError).errorState

            # Defined Errors
            defined_errors = [error.value for error in cluster.Enums.ErrorStateEnum
                              if (error != cluster.Enums.ErrorStateEnum.kUnknownEnumValue or
                                  error != cluster.Enums.ErrorStateEnum.kNoError)]

            in_range = (0x80 <= event_data.errorStateID <= 0xBF)
            asserts.assert_true(event_data.errorStateID in defined_errors
                                or in_range, "Event has an invalid ID value!")
            if in_range:
                asserts.assert_true(event_data.errorStateLabel is not None, "ErrorStateLabel should be populated")

            # STEP 4: TH reads from the DUT the OperationalState attribute
            self.step(4)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kError)
        else:
            self.skip_step(2)
            self.skip_step(3)
            self.skip_step(4)

    ############################
    #   TEST CASE 2.5
    ############################
    def STEPS_TC_OPSTATE_BASE_2_5(self) -> list[TestStep]:
        steps = [TestStep(1, "Commissioning, already done", is_commissioning=True),
                 TestStep(2, "Set up a subscription to the OperationCompletion event"),
                 TestStep(3, "Manually put the DUT into a state wherein it can receive a Start Command"),
                 TestStep(4, "TH sends Start command to the DUT"),
                 TestStep(5, "TH reads from the DUT the CountdownTime attribute"),
                 TestStep(6, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(7, "TH waits for initial-countdown-time"),
                 TestStep(8, "TH sends Stop command to the DUT"),
                 TestStep(9, "TH waits for OperationCompletion event"),
                 TestStep(10, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(11, "Restart DUT"),
                 TestStep(12, "TH waits for {PIXIT.WAITTIME.REBOOT}"),
                 TestStep(13, "TH sends Start command to the DUT"),
                 TestStep(14, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(15, "TH sends Pause command to the DUT"),
                 TestStep(16, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(17, "TH waits for half of initial-countdown-time"),
                 TestStep(18, "TH sends Resume command to the DUT"),
                 TestStep(19, "TH reads from the DUT the OperationalState attribute"),
                 TestStep(20, "TH waits for initial-countdown-time"),
                 TestStep(21, "TH sends Stop command to the DUT"),
                 TestStep(22, "TH waits for OperationCompletion event")
                 ]
        return steps

    async def TEST_TC_OPSTATE_BASE_2_5(self, endpoint=1):
        cluster = self.test_info.cluster
        attributes = cluster.Attributes
        commands = cluster.Commands
        events = cluster.Events

        self.init_test()

        asserts.assert_true('PIXIT.WAITTIME.REBOOT' in self.matter_test_config.global_test_params,
                            "PIXIT.WAITTIME.REBOOT must be included on the command line in "
                            "the --int-arg flag as PIXIT.WAITTIME.REBOOT:<wait time>")

        wait_time_reboot = self.matter_test_config.global_test_params['PIXIT.WAITTIME.REBOOT']

        if wait_time_reboot == 0:
            asserts.fail("PIXIT.WAITTIME.REBOOT shall be higher than 0.")

        # STEP 1: Commission DUT to TH (can be skipped if done in a preceding test)
        self.step(1)

        # STEP 2: Set up a subscription to the OperationCompletion event
        self.step(2)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.E01")):
            # Subscribe to Events and when they are sent push them to a queue for checking later
            events_callback = EventSpecificChangeCallback(events.OperationCompletion)
            await events_callback.start(self.default_controller,
                                        self.dut_node_id,
                                        endpoint)

        # STEP 3: Manually put the DUT into a state wherein it can receive a Start Command
        self.step(3)
        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="OnFault",
                                         param=cluster.Enums.ErrorStateEnum.kNoError)

        self.send_manual_or_pipe_command(name="OperationalStateChange",
                                         device=self.device,
                                         operation="Stop")

        # STEP 4: TH sends Start command to the DUT
        self.step(4)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") and
                           self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
            await self.send_cmd_expect_response(endpoint=endpoint,
                                                cmd=commands.Start(),
                                                expected_response=cluster.Enums.ErrorStateEnum.kNoError)

        # STEP 5: TH reads from the DUT the CountdownTime attribute
        self.step(5)
        if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0002")):
            initial_countdown_time = await self.read_expect_success(endpoint=endpoint,
                                                                    attribute=attributes.CountdownTime)

        if initial_countdown_time is not NullValue:
            # STEP 6: TH reads from the DUT the OperationalState attribute
            self.step(6)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kRunning)

            # STEP 7: TH waits for initial-countdown-time
            self.step(7)
            time.sleep(initial_countdown_time)

            # STEP 8: TH sends Stop command to the DUT
            self.step(8)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") and
                               self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
                await self.send_cmd_expect_response(endpoint=endpoint,
                                                    cmd=commands.Stop(),
                                                    expected_response=cluster.Enums.ErrorStateEnum.kNoError)

            # STEP 9: TH waits for OperationCompletion event
            self.step(9)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.E01")):
                event_data = events_callback.wait_for_event_report()

                asserts.assert_equal(event_data.completionErrorCode, cluster.Enums.ErrorStateEnum.kNoError,
                                     f"Completion event error code mismatched from expectation on endpoint {endpoint}.")

                if event_data.totalOperationalTime is not NullValue:
                    asserts.assert_less_equal(initial_countdown_time, event_data.totalOperationalTime,
                                              f"The total operation time shall be at least {initial_countdown_time:.1f}")

                asserts.assert_equal(0, event_data.pausedTime,
                                     f"Paused time ({event_data.pausedTime}) shall be zero")

            # STEP 10: TH reads from the DUT the OperationalState attribute
            self.step(10)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kStopped)

            # STEP 11: Restart DUT
            self.step(11)
            # In CI environment, the STOP coommand (step 8) already resets the variables. Only ask for
            # reboot outside CI environment.
            if not self.is_ci:
                input("Press Enter when done.\n")

            # STEP 12: TH waits for {PIXIT.WAITTIME.REBOOT}
            self.step(12)
            time.sleep(wait_time_reboot)

            # STEP 13: TH sends Start command to the DUT
            self.step(13)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C02.Rsp") and
                               self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
                await self.send_cmd_expect_response(endpoint=endpoint,
                                                    cmd=commands.Start(),
                                                    expected_response=cluster.Enums.ErrorStateEnum.kNoError)

            # STEP 14: TH reads from the DUT the OperationalState attribute
            self.step(14)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kRunning)

            # STEP 15: TH sends Pause command to the DUT
            self.step(15)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C00.Rsp") and
                               self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
                await self.send_cmd_expect_response(endpoint=endpoint,
                                                    cmd=commands.Pause(),
                                                    expected_response=cluster.Enums.ErrorStateEnum.kNoError)

            # STEP 16: TH reads from the DUT the OperationalState attribute
            self.step(16)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kPaused)

            # STEP 17: TH waits for half of initial-countdown-time
            self.step(17)
            time.sleep((initial_countdown_time / 2))

            # STEP 18: TH sends Resume command to the DUT
            self.step(18)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C03.Rsp") and
                               self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
                await self.send_cmd_expect_response(endpoint=endpoint,
                                                    cmd=commands.Resume(),
                                                    expected_response=cluster.Enums.ErrorStateEnum.kNoError)

            # STEP 19: TH reads from the DUT the OperationalState attribute
            self.step(19)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.A0004")):
                await self.read_and_expect_value(endpoint=endpoint,
                                                 attribute=attributes.OperationalState,
                                                 expected_value=cluster.Enums.OperationalStateEnum.kRunning)

            # STEP 20: TH waits for initial-countdown-time
            self.step(20)
            time.sleep(initial_countdown_time)

            # STEP 21: TH sends Stop command to the DUT
            self.step(21)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.C01.Rsp") and
                               self.check_pics(f"{self.test_info.pics_code}.S.C04.Tx")):
                await self.send_cmd_expect_response(endpoint=endpoint,
                                                    cmd=commands.Stop(),
                                                    expected_response=cluster.Enums.ErrorStateEnum.kNoError)

            # STEP 22: TH waits for OperationCompletion event
            self.step(22)
            if self.pics_guard(self.check_pics(f"{self.test_info.pics_code}.S.E01")):
                event_data = events_callback.wait_for_event_report()

                asserts.assert_equal(event_data.completionErrorCode, cluster.Enums.ErrorStateEnum.kNoError,
                                     f"Completion event error code mismatched from expectation on endpoint {endpoint}.")

                if event_data.totalOperationalTime is not NullValue:
                    expected_value = (1.5 * initial_countdown_time)

                    asserts.assert_less_equal(expected_value, event_data.totalOperationalTime,
                                              f"The total operation time shall be at least {expected_value:.1f}")

                expected_value = (0.5 * initial_countdown_time)
                asserts.assert_less_equal(expected_value, event_data.pausedTime,
                                          f"Paused time ({event_data.pausedTime}) shall be at least {expected_value:.1f}")
        else:
            self.skip_step(6)
            self.skip_step(7)
            self.skip_step(8)
            self.skip_step(9)
            self.skip_step(10)
            self.skip_step(11)
            self.skip_step(12)
            self.skip_step(13)
            self.skip_step(14)
            self.skip_step(15)
            self.skip_step(16)
            self.skip_step(17)
            self.skip_step(18)
            self.skip_step(19)
            self.skip_step(20)
            self.skip_step(21)
            self.skip_step(22)
