@@ -143,6 +143,75 @@ describe("Extension: HomeAssistant", () => {
143143 expect ( weeklyScheduleConfig ! . discovery_payload . json_attributes_template ) . toContain ( "schedule" ) ;
144144 } ) ;
145145
146+ it ( "Should discover SONOFF TRVZB schedule sensor with json_attributes" , ( ) => {
147+ // Create a SONOFF TRVZB expose definition with schedule (composite type)
148+ const trvzbExposes = [
149+ {
150+ type : "climate" ,
151+ features : [
152+ {
153+ name : "occupied_heating_setpoint" ,
154+ property : "occupied_heating_setpoint" ,
155+ type : "numeric" ,
156+ access : 7 ,
157+ value_min : 4 ,
158+ value_max : 35 ,
159+ value_step : 0.5 ,
160+ } ,
161+ { name : "local_temperature" , property : "local_temperature" , type : "numeric" , access : 5 } ,
162+ { name : "system_mode" , property : "system_mode" , type : "enum" , access : 7 , values : [ "off" , "auto" , "heat" ] } ,
163+ { name : "running_state" , property : "running_state" , type : "enum" , access : 5 , values : [ "idle" , "heat" ] } ,
164+ ] ,
165+ } ,
166+ {
167+ type : "composite" ,
168+ name : "schedule" , // This is the key - "schedule", not "weekly_schedule"
169+ property : "weekly_schedule" ,
170+ label : "Schedule" ,
171+ access : 3 ,
172+ category : "config" ,
173+ features : [
174+ { name : "sunday" , property : "sunday" , type : "text" , access : 3 } ,
175+ { name : "monday" , property : "monday" , type : "text" , access : 3 } ,
176+ { name : "tuesday" , property : "tuesday" , type : "text" , access : 3 } ,
177+ { name : "wednesday" , property : "wednesday" , type : "text" , access : 3 } ,
178+ { name : "thursday" , property : "thursday" , type : "text" , access : 3 } ,
179+ { name : "friday" , property : "friday" , type : "text" , access : 3 } ,
180+ { name : "saturday" , property : "saturday" , type : "text" , access : 3 } ,
181+ ] ,
182+ } ,
183+ ] ;
184+
185+ // Create a mock device with TRVZB exposes
186+ const mockDevice = {
187+ definition : { vendor : "SONOFF" , model : "TRVZB" } ,
188+ isDevice : ( ) => true ,
189+ isGroup : ( ) => false ,
190+ options : { ID : "0x1234567890abcdef" } ,
191+ exposes : ( ) => trvzbExposes ,
192+ zh : { endpoints : [ ] } ,
193+ name : "test_trvzb" ,
194+ } ;
195+
196+ // @ts -expect-error private method
197+ const configs = extension . getConfigs ( mockDevice ) ;
198+
199+ // Find the schedule sensor config
200+ const scheduleConfig = configs . find ( ( c ) => c . object_id === "schedule" || c . object_id === "weekly_schedule" ) ;
201+
202+ expect ( scheduleConfig ) . toBeDefined ( ) ;
203+ expect ( scheduleConfig . type ) . toBe ( "sensor" ) ;
204+ expect ( scheduleConfig . discovery_payload . icon ) . toBe ( "mdi:calendar-clock" ) ;
205+ expect ( scheduleConfig . discovery_payload . value_template ) . toContain ( "days configured" ) ;
206+ expect ( scheduleConfig . discovery_payload . value_template ) . not . toContain ( "truncate" ) ;
207+
208+ // Most importantly: verify json_attributes_topic is set to true (will be converted to actual topic)
209+ expect ( scheduleConfig . discovery_payload . json_attributes_topic ) . toBe ( true ) ;
210+ expect ( scheduleConfig . discovery_payload . json_attributes_template ) . toBeDefined ( ) ;
211+ expect ( scheduleConfig . discovery_payload . json_attributes_template ) . toContain ( "schedule" ) ;
212+ expect ( scheduleConfig . discovery_payload . json_attributes_template ) . toContain ( "weekly_schedule" ) ;
213+ } ) ;
214+
146215 it ( "Should not have duplicate type/object_ids in a mapping" , async ( ) => {
147216 const duplicated : string [ ] = [ ] ;
148217
0 commit comments