Skip to content

Commit 90b7aff

Browse files
committed
First cut of a Q quality test
1 parent e52b7da commit 90b7aff

File tree

1 file changed

+153
-0
lines changed

1 file changed

+153
-0
lines changed

src/python_testing/TC_DEM_2_10.py

+153
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,153 @@
1+
#
2+
# Copyright (c) 2024 Project CHIP Authors
3+
# All rights reserved.
4+
#
5+
# Licensed under the Apache License, Version 2.0 (the "License");
6+
# you may not use this file except in compliance with the License.
7+
# You may obtain a copy of the License at
8+
#
9+
# http://www.apache.org/licenses/LICENSE-2.0
10+
#
11+
# Unless required by applicable law or agreed to in writing, software
12+
# distributed under the License is distributed on an "AS IS" BASIS,
13+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
# See the License for the specific language governing permissions and
15+
# limitations under the License.
16+
# pylint: disable=invalid-name
17+
18+
# See https://github.com/project-chip/connectedhomeip/blob/master/docs/testing/python.md#defining-the-ci-test-arguments
19+
# for details about the block below.
20+
#
21+
# === BEGIN CI TEST ARGUMENTS ===
22+
# test-runner-runs: run1
23+
# test-runner-run/run1/app: ${ENERGY_MANAGEMENT_APP}
24+
# test-runner-run/run1/factoryreset: True
25+
# test-runner-run/run1/quiet: True
26+
# test-runner-run/run1/app-args: --discriminator 1234 --KVS kvs1 --trace-to json:${TRACE_APP}.json --enable-key 000102030405060708090a0b0c0d0e0f --featureSet 0x7c
27+
# test-runner-run/run1/script-args: --storage-path admin_storage.json --commissioning-method on-network --discriminator 1234 --passcode 20202021 --hex-arg enableKey:000102030405060708090a0b0c0d0e0f --endpoint 1 --trace-to json:${TRACE_TEST_JSON}.json --trace-to perfetto:${TRACE_TEST_PERFETTO}.perfetto
28+
# === END CI TEST ARGUMENTS ===
29+
30+
"""Define Matter test case TC_DEM_2_10."""
31+
32+
33+
import logging
34+
import datetime
35+
import time
36+
37+
import chip.clusters as Clusters
38+
from chip.interaction_model import Status
39+
from matter_testing_support import ClusterAttributeChangeAccumulator, MatterBaseTest, TestStep, async_test_body, default_matter_test_main
40+
from mobly import asserts
41+
from TC_DEMTestBase import DEMTestBase
42+
43+
logger = logging.getLogger(__name__)
44+
45+
46+
class TC_DEM_2_10(MatterBaseTest, DEMTestBase):
47+
"""Implementation of test case TC_DEM_2_10."""
48+
49+
def desc_TC_DEM_2_10(self) -> str:
50+
"""Return a description of this test."""
51+
return "4.1.3. [TC-DEM-2.10] This test case verifies attributes of the Device Energy Mangement cluster server having the Q quality."
52+
53+
def pics_TC_DEM_2_10(self):
54+
"""Return the PICS definitions associated with this test."""
55+
pics = [
56+
# Depends on Feature 05 (ForecastAdjustment) & Feature 02 (StateForecastReporting)
57+
"DEM.S.F05", "DEM.S.F02"
58+
]
59+
return pics
60+
61+
def steps_TC_DEM_2_10(self) -> list[TestStep]:
62+
"""Execute the test steps."""
63+
steps = [
64+
TestStep("1", "Commission DUT to TH"),
65+
TestStep("2", "TH reads from the DUT the Featuremap attribute",
66+
"Verify that the DUT response contains the Featuremap attribute. Verify ForecastAdjustment and StateForecastReporting is supported. Verify PowerForecastReporting is not supported."),
67+
TestStep("3", "TH reads TestEventTriggersEnabled attribute from General Diagnostics Cluster",
68+
"Value has to be 1 (True)"),
69+
TestStep("4", "TH sends TestEventTrigger command to General Diagnostics Cluster on Endpoint 0 with EnableKey field set to PIXIT.DEM.TESTEVENT_TRIGGERKEY and EventTrigger field set to PIXIT.DEM.TESTEVENTTRIGGER for Forecast Adjustment Test Event",
70+
"Verify DUT responds w/ status SUCCESS(0x00)"),
71+
TestStep("4a", "TH reads from the DUT the ESAState",
72+
"Value has to be 0x01 (Online)"),
73+
TestStep("4b", "TH reads from the DUT the Forecast",
74+
"Value has to include slots[0].MinDurationAdjustment, slots[0].MaxDurationAdjustment"),
75+
TestStep("4c", "TH reads from the DUT the OptOutState",
76+
"Value has to be 0x00 (NoOptOut)"),
77+
TestStep("5", "Set up a subscription to the Forecast attribute, with MinIntervalFloor set to 0, MaxIntervalCeiling set to 10 and KeepSubscriptions set to false",
78+
"Subscription successfully established"),
79+
TestStep("6", "TH sends TestEventTrigger command to General Diagnostics Cluster on Endpoint 0 with EnableKey field set to PIXIT.DEM.TESTEVENT_TRIGGERKEY and EventTrigger field set to PIXIT.DEM.TESTEVENTTRIGGER for User Opt-out Local Optimization Test Event",
80+
"Verify DUT responds w/ status SUCCESS(0x00)"),
81+
TestStep("6a", "TH reads from the DUT the ESAState",
82+
"Value has to be 0x01 (Online)"),
83+
TestStep("6b", "TH reads from the DUT the OptOutState",
84+
"Value has to be 0x02 (LocalOptOut)"),
85+
TestStep("7", "TH sends command ModifyForecastRequest with ForecastID=Forecast.ForecastID, SlotAdjustments[0].{SlotIndex=0, Duration=Forecast.Slots[0].MinDurationAdjustment}, Cause=GridOptimization",
86+
"Verify DUT responds w/ status SUCCESS(0x00)"),
87+
TestStep("8", "TH counts all report transactions with an attribute report for the Forecast attribute over the next Forecast.Slots[0].MinDurationAdjustment}",
88+
"TH verifies that numberOfReportsReceived <= 2 + Forecast.Slots[0].MinDurationAdjustment}"),
89+
TestStep("9", "TH sends TestEventTrigger command to General Diagnostics Cluster on Endpoint 0 with EnableKey field set to PIXIT.DEM.TESTEVENT_TRIGGERKEY and EventTrigger field set to PIXIT.DEM.TESTEVENTTRIGGER for Forecast Adjustment Test Event Clear",
90+
"Verify DUT responds w/ status SUCCESS(0x00)"),
91+
]
92+
93+
return steps
94+
95+
@async_test_body
96+
async def test_TC_DEM_2_10(self):
97+
# pylint: disable=too-many-locals, too-many-statements
98+
"""Run the test steps."""
99+
self.step("1")
100+
# Commission DUT - already done
101+
102+
self.step("2")
103+
await self.validate_feature_map([Clusters.DeviceEnergyManagement.Bitmaps.Feature.kForecastAdjustment,
104+
Clusters.DeviceEnergyManagement.Bitmaps.Feature.kStateForecastReporting],
105+
[Clusters.DeviceEnergyManagement.Bitmaps.Feature.kPowerForecastReporting])
106+
107+
self.step("3")
108+
await self.check_test_event_triggers_enabled()
109+
110+
self.step("4")
111+
await self.send_test_event_trigger_forecast_adjustment()
112+
113+
self.step("4a")
114+
await self.check_dem_attribute("ESAState", Clusters.DeviceEnergyManagement.Enums.ESAStateEnum.kOnline)
115+
116+
self.step("4b")
117+
forecast = await self.read_dem_attribute_expect_success(attribute="Forecast")
118+
asserts.assert_is_not_none(forecast.slots[0].minDurationAdjustment)
119+
asserts.assert_is_not_none(forecast.slots[0].maxDurationAdjustment)
120+
121+
self.step("4c")
122+
await self.check_dem_attribute("OptOutState", Clusters.DeviceEnergyManagement.Enums.OptOutStateEnum.kNoOptOut)
123+
124+
self.step("5")
125+
sub_handler = ClusterAttributeChangeAccumulator(Clusters.DeviceEnergyManagement)
126+
await sub_handler.start(self.default_controller, self.dut_node_id, self.matter_test_config.endpoint)
127+
sub_handler.reset()
128+
129+
self.step("6")
130+
await self.send_test_event_trigger_user_opt_out_local()
131+
132+
self.step("6a")
133+
await self.check_dem_attribute("ESAState", Clusters.DeviceEnergyManagement.Enums.ESAStateEnum.kOnline)
134+
135+
self.step("6b")
136+
await self.check_dem_attribute("OptOutState", Clusters.DeviceEnergyManagement.Enums.OptOutStateEnum.kLocalOptOut)
137+
138+
self.step("7")
139+
slotAdjustments = [Clusters.DeviceEnergyManagement.Structs.SlotAdjustmentStruct(slotIndex=0, duration=forecast.slots[0].minDurationAdjustment)]
140+
await self.send_modify_forecast_request_command(forecast.forecastID, slotAdjustments, Clusters.DeviceEnergyManagement.Enums.AdjustmentCauseEnum.kGridOptimization, expected_status=Status.Success)
141+
142+
self.step("8")
143+
time.sleep(forecast.slots[0].minDurationAdjustment)
144+
145+
count = sub_handler.attribute_report_counts[Clusters.DeviceEnergyManagement.Attributes.Forecast]
146+
asserts.assert_less_equal(count, 10, "More than 10 reports received")
147+
148+
self.step("9")
149+
await self.send_test_event_trigger_forecast_adjustment_clear()
150+
151+
152+
if __name__ == "__main__":
153+
default_matter_test_main()

0 commit comments

Comments
 (0)