[Device Support Request] TS0601 _TZE200_hue3yfsn / TV02 Zigbee TRV

Is your feature request related to a problem? Please describe.
I bought this thermostat from AliExpress. It's possible to pair with ZHA, but no entities are exposed.
Describe the solution you'd like
Ideally, I'd like to control all settings these Tuya based thermostats have. I know that Zigbee2MQTT seems to be able to do that (Source)
Device signature
  "node_descriptor": "NodeDescriptor(logical_type=<LogicalType.EndDevice: 2>, complex_descriptor_available=0, user_descriptor_available=0, reserved=0, aps_flags=0, frequency_band=<FrequencyBand.Freq2400MHz: 8>, mac_capability_flags=<MACCapabilityFlags.AllocateAddress: 128>, manufacturer_code=4098, maximum_buffer_size=82, maximum_incoming_transfer_size=82, server_mask=11264, maximum_outgoing_transfer_size=82, descriptor_capability_field=<DescriptorCapability.NONE: 0>, *allocate_address=True, *is_alternate_pan_coordinator=False, *is_coordinator=False, *is_end_device=True, *is_full_function_device=False, *is_mains_powered=False, *is_receiver_on_when_idle=False, *is_router=False, *is_security_capable=False)",
  "endpoints": {
    "1": {
      "profile_id": 260,
      "device_type": "0x0051",
      "in_clusters": [
        "0x0000",
        "0x0004",
        "0x0005",
        "0xef00"
      ],
      "out_clusters": [
        "0x000a",
        "0x0019"
      ]
    }
  },
  "manufacturer": "_TZE200_hue3yfsn",
  "model": "TS0601",
  "class": "zigpy.device.Device"
}

Additional context
The thermostat has no branding whatsoever (neither the device itself, nor the packaging material), I can't tell who is the actual manufacturer. In the included manual it's refered to as TV02 Zigbee Thermostat Radiator Valve
I bought it from this link: AliExpress

Vielleicht kann das weiter helfen, ich hab meine TRVs angebunden.
10                  frost: 0                           Frost Protection
101                KSSW: 1 SECOND
102                KCWD: 5 度                  Open Window
104                SSWD: 21 度                 Comfortable Temp
105                JLWD: 17 度                  ECO Temp
107                Heating_Stopping: 0      Heating Stop
108                mod_program001:         Zeitplan Montag
109                wed_program003:
110                fri_program005:
111                sun_program007:
112                tue_program002:
113                thur_program004:
114                sat_program006:
115                online: 1
16                  temp_set: 18.5 ℃ (SET.Temp)
2                    mode: auto
24                  temp_current: 21.8 ℃
27                  temp_correction: 0.1
31                  work_days: all
32                  holiday_temp_set: 17 ℃ Holiday Mode
35                  battery_percentage: 100 %;
40                  child_lock: 0
45                  fault: 1
46                  holiday_set: 201
8                    window_check: 0 ;

Can you state more precisely where this information needs to go to?

@diti1377 You was writing in Iobroker that one user have written one quirk for one TRV in ZHA that have the same DPs like this but i cant finding the user name and the quirk.
Can you pleas putting my in the right direction to finding it pleas ?

If you is adding the model_id to more signatures and more then one is matching i think ZHA is using the first match (or the last one i dont knowing the logic).
Your device is having one on/off switch so i think its one Moes or one Sas that is loaded.
You can see the name of the loaded quirk in the last line on the device profile or on the device card.
Deleting all your added model_ids and only adding it to the ZonnsmartTV01_ZG then its looks matching your device DPs and restarting HA.
With the last ZonnsmartTV01_ZG you shall not do the ZAH fix then its not using the Moes TRV quirk so only adding the model _id or you is getting errors and HA is not starting.

Ok, maybe I should clarify that I tested each class separately one at a time and didn't add the model info to all classes simultaneously. Each time with a similar result.

This TRV is bit strange. It shares like a 95% of DPs with Lidl, but it's completely different device. Actually in one listing you can find the word Zonnsmart. Look here https://de.aliexpress.com/item/1005003190631469.html (Zonnsmart it's not in the description but in comparison image in Energy Saving section)
My assumption is that it needs to be build on top of the current Zonnsmart integration.
@Droggel00 The last two days I was observing mine and it never publishes current temperature. The only option is to restart the device. Does somebody know if it has to be manually requested?

If using Zonnsmart quirk and correcting it for different DP, is one problem with the Zonnsmart implementation its dont updating the local temperature and the same person that  was doing the Zonnsmart quirk is doing  the same in Z2M and they is having the same problem with the device so very likely some strange in the device firmware.
One way is using the "Moes" quirk that is the one with most functions and working well and adjusting the DP and functions for SHENZHEN RSH TRVs and see if its working better.
If setting zhaquirks,tuya debug in HA you can see the DP commands sent and revived is you getting any with the DP for local temperature or some other that can being that ?
Moes TRVs users is sending Calibrating local temperature from HA automation for getting more frequent update then one time in the hour that the Moes (and most tuya) TRVs is doing.

I was able to extend the zonnsmart quirk with ECO_TEMP, CONFORT_TEMP and TEMP_CORRECTION. I'm pretty sure that this device is ZONNSMART because it uses the same DPs.
As was said by @dodekaphilist here by just adding it to current ZONNSMART quirk you'll get current temp, set temp, turn heating on/off. This attributes can be controlled using HA frontend, but by sending values over developer tools you can control child lock, window detection and mode as well. I've extended this quirk with ECO_TEMP, COMFORT_TEMP and TEMP_CORRECTION (aka calibration) which was pretty easy. After that I looked at zigbee2mqtt, now I'm sure that this zonnsmart quirk is just missing a lot of attributes.
I can extend this quirk, that's no problem, but I have no idea how to get entities like child_lock, mode, eco_temp, etc. appear on HA frontend. @MattWestb can you navigate me in right direction?
About the current-temp-bug you were right, I could force the publishing by setting the local temperature calibration value. But I'm not the only person who is experiencing this behaviour. Same device same solution and here as well, but another solution. One user offered that he'll try to sniff the communication with tyua hub, we need to be patient.

Great findings and work !!
You dont need using the development tool if you like only manage cluster from the device card and you is having all functions on the new tuya clusters for your device like window detection and child lock if they is implanted OK.
The original implanting was done early in ZHA and all functions was not discovered but the dev have implanting them in Z2M so shall being possible doing i ZHA.
So this is one Zonnsmart TV01-ZG with LED display on the side :-))
Shall i making on PR for adding it in the quirk so user can start using it in one easy way ?
The original implantation was not using presets in ZHA clima component so its have very little working modes in ZHA. Adding them is prity easy but  must being made in both the quirk and in ZHA or its braking the function of changing mode in ZHA.
You can looking how the Moes TRVs is implanted and copy it.
I  have making one PR for adding this future in the Siterwell TRV but i cant getting it thru then i braking many tests in Zogpy :-((
The problem with Siterwell is that is many in use so not nice braking them  but it can being needed doing for getting all function working in ZHA.
Looks on my Siterwell upgrading project https://github.com/zigpy/zha-device-handlers/discussions/1084.
Switched and reporting alarm and status is coming then https://github.com/zigpy/zha-device-handlers/issues/1061 is getting working OK its possible implanting this functions in the same way but its not tested in production but is coming very soon.
One more time great work done !!

Wow thanks about the "manage cluster" info, this could save me a lot of time. But better now than never :)
Tomorrow I'll add those missing DPs and do PR. Just to be noted for known reasons I don't plan to integrate scheduler. After that we can work on displaying those entities on HA frontend.

If you like implanting presets in ZHA i have making one climate.py for ZS with the hue3yfs  ID and the normal ZS ones that you can patching in your HA container and getting the presets working (I have copy the Moes TRV that is having most presets and if you dont need some its only deleting them later but good for testing).
If running HA 2021.11 copy the extracted climate.py in to your HA config directory.
Open one terminal in your HA docker container and copy the new file to its right place:
cd  /usr/src/homeassistant/homeassistant/components/zha/
cp /config/climate.py climate.py

Have moving the device to ZS in the tuya TRV matrix and setting status "working with quirk in PR" so its looks better.

Currently I've only expanded the known DPs and tested them by setting/getting the values manually.
Following DPs works and they behaviour is more o less clear:
-MODE        2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x0402 (command 0x0001)
-WINDOW      2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x0108 (command 0x0001)
-FROST       2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x010a (command 0x0001)
-HEATTEMP    2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 170] for attribute 0x0210 (command 0x0001)
-CURTEMP     2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 205] for attribute 0x0218 (command 0x0001)
-CORRTEMP    2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 0] for attribute 0x021b (command 0x0001)
-WORKDAYS    2021-11-04 19:27:40 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x041f (command 0x0001)
-HOLIDAYTEMP 2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 170] for attribute 0x0220 (command 0x0001)
-BATT        2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 100] for attribute 0x0223 (command 0x0001)
-CHILDLOCK   2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x0128 (command 0x0001)
-BOOST       2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 0] for attribute 0x0265 (command 0x0001)
-COMFORTTEMP 2021-11-04 19:27:42 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 210] for attribute 0x0268 (command 0x0001)
-ECOTEMP     2021-11-04 19:27:42 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 170] for attribute 0x0269 (command 0x0001)
-HEATSTOP    2021-11-04 19:27:42 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x016b (command 0x0001)

In those ones I don't understand the meaning or values.
?FAULTY      2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0] for attribute 0x052d (command 0x0001)
?HOLIDAY     2021-11-04 19:27:41 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [50, 48, 50, 49, 48, 49, 48, 49, 48, 49, 48, 49, 50, 48, 50, 49, 48, 49, 48, 49, 48, 49, 48, 49] for attribute 0x032e (command 0x0001)
?WINDOW TEMP 2021-11-04 19:27:42 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [0, 0, 0, 210] for attribute 0x0266 (command 0x0001)
?ONLINE      2021-11-04 19:27:47 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [1] for attribute 0x0473 (command 0x0001)

Faulty - what fault is reported?
Holiday - this is holiday duration not temperature (holiday temp works), but the format is unknown and I don't have Tuya hub to test it.
Window Temp value is used to recognize opened window. It should represent temp drop, but the parameter 210 is too much.
Online doesn't make sense, how can device publish online=0 if the connection is down ???

 Now I can work on ZHA integration.

Siterwell is having valve detect / anti calk function and if the valve is jammed the valve is sending one alarm. I was testing it by setting the setpoint to high and the valve was trying getting the temperature up but was failing after some time and was having the ! in the display and and sending the DP for valve jammed.
I think the best is as you have saying all known DP to working OK and try finding the function for the not known function and leave the scheduler until ZHA have getting better support for it.
Look little on Moes and the LIDL implantation and you can see different ways for window and holiday is working and i dont knowing if the online  is called ping in some issues but i dont knowing how it working.

I was able to implement:
- heating operation off/heat
- present manual/schedule/holiday
- opened window detection
- child lock
- fault (not able to test)
- temperature offset

Probably this TRV will be needing its own class because I can't test it with original ZONNSMART. The behaviour like ability to turn it off is missing on most devices like SITERWELL or LIDL.
Unique behaviour of this TRV:
###Off
You can turn this TRV off, by setting ZONNSMART_HEATING_STOPPING = 0x016B to 1. On the TRV will be show HS (heating stopped) and you can't do anything till you deactivate it.
###Present
Manual and Schedule works like expected but holiday mode cannot be started by selecting the mode. It only shows the holiday mode temperature and after 5sec it switches back to schedule mode. (FYI holiday mode is activated automatically by setting begin and end timestamp = not implemented)
###Frost Protection (not implemeted)
I don't know how to implement this one, because it's like one of those Present Modes. After setting ZONNSMART_FROST_PROTECT_ATTR = 0x010a attribute, on TRV will be shown AF (antifreeze), it sets temperature to 8 degrees and you cannot do anything until you disable this.
###Don't publishes room temperature
This TRV never publishes room temperature, it has to be manually requested. Currently the only way is to set temperature offset (even with 0), after that the room temperature will be published.
If someone will test it, here is the quirk: valve.zip but for presets to work, you have to add to /components/zha/climate.py following lines:
@STRICT_MATCH(
    channel_names=CHANNEL_THERMOSTAT,
    manufacturers={
        "_TZE200_hue3yfsn",
        },
)

class ZONNSMARTThermostat(Thermostat):
    """ZONNSMART Thermostat implementation"""
    def __init__(self, unique_id, zha_device, channels, **kwargs):
        """Initialize ZHA Thermostat instance."""
        super().__init__(unique_id, zha_device, channels, **kwargs)
            self._presets = [
            PRESET_SCHEDULE,
            PRESET_NONE,
            PRESET_AWAY,
        ]
        self._supported_flags |= SUPPORT_PRESET_MODE

    async def async_attribute_updated(self, record):
        """Handle attribute update from device."""
        if record.attr_name == "operation_preset":
            if record.value == 0:
                self._preset = PRESET_SCHEDULE
            if record.value == 1:
                self._preset = PRESET_NONE
            if record.value == 3:
                self._preset = PRESET_AWAY
        await super().async_attribute_updated(record)

    async def async_preset_handler(self, preset: str, enable: bool = False) -> bool:
        """Set the preset mode."""
        mfg_code = self._zha_device.manufacturer_code
        if not enable:
            return await self._thrm.write_attributes(
                {"operation_preset": 1}, manufacturer=mfg_code
            )
        if preset == PRESET_SCHEDULE:
            return await self._thrm.write_attributes(
                {"operation_preset": 0}, manufacturer=mfg_code
            )
        if preset == PRESET_AWAY:
            return await self._thrm.write_attributes(
                {"operation_preset": 3}, manufacturer=mfg_code
            )
        return False

"###Present
Manual and Schedule works like expected but holiday mode cannot be started by selecting the mode. It only shows the holiday mode temperature and after 5sec it switches back to schedule mode."
Holiday mode often has date/time of start and time duration. If present time is after the values were set it switches back to Schedule after some time. That 5 sec. for Maxsmart is to start setting the parameters on the TRV.
"###Frost Protection (not implemeted)"
For frost protection you would need to add another switch and a proper code + bus listener
Catch the attribute and set temperature manually if you don't have an attribute for it.
ZONNSMARTManufCluster:
        elif attrid == ZONNSMART_FROST_PROTECT_ATTR:
            self.endpoint.device.thermostat_bus.listener_event(
                "temperature_change",
                self.DIRECT_MAPPED_ATTRS[ZONNSMART_TARGET_TEMP_ATTR][0],
                800)
           self.endpoint.device.frost_protection_bus.listener_event(
                "frost_protection_change", mode)

Copy&paste child lock class and rename it to frost protection.
Add another endpoint to ZonnsmartTV01_ZG
            3: {
                PROFILE_ID: zha.PROFILE_ID,
                DEVICE_TYPE: zha.DeviceType.ON_OFF_SWITCH,
                INPUT_CLUSTERS: [
                    ZONNSMARTFrostProtection,
                ],
                OUTPUT_CLUSTERS: [],
            },

Don't forget to INIT bus in ZonnsmartTV01_ZG ->def init
self.frost_protection_bus= Bus()

If above code will not work[probably won't] do three more steps:
Add ZONNSMARTManufClusterSelf variable like below:
ZONNSMART_HOLIDAY_DATETIME_ATTR = 0x032e  # holiday mode date and time of begin and end
ZONNSMART_WEEK_FORMAT_ATTR = 0x041f  # # [0] 5+2 days [1] 6+1 days, [2] 7 days
ZONNSMART_FAULT_DETECTION_ATTR = 0x052d  # [0] no fault [1] fault detected
ZONNSMARTManufClusterSelf = None

Add INIT to ZONNSMARTManufCluster before manufacturer_attributes:
    def __init__(self, *args, **kwargs):
        """Init."""
        super().__init__(*args, **kwargs)
        self.endpoint.device.ZONNSMARTManufCluster .add_listener(self)
        global ZONNSMARTManufClusterSelf
        ZONNSMARTManufClusterSelf = self

Then use that variable in the write_attributes of ZONNSMARTFrostProtection
Change line to:
        if has_change:
            return await ZONNSMARTManufClusterSelf .endpoint.tuya_manufacturer.write_attributes(
                {ZONNSMART_FROST_PROTECT_ATTR: value}, manufacturer=manufacturer
            )

That's is needed because your ZONNSMARTFrostProtection is on endpoint 3 and ZONNSMART_FROST_PROTECT_ATTR is on endpoint 1.
If you do self.*** it assumes that the self.*** is on same endpoint - but here it isn't.
We just created a reference to endpoint 1 class.

###Present
Manual and Schedule works like expected but holiday mode cannot be started by selecting the mode. It only shows the holiday mode temperature and after 5sec it switches back to schedule mode."

Holiday mode often has date/time of start and time duration. If present time is after the values were set it switches back to Schedule after some time. That 5 sec. for Maxsmart is to start setting the parameters on the TRV.

Yes I know how it works, I wrote that it starts automatically by setting begin and end time, but here is the format different than the Maxsmart. This TRV uses only one attribute, its value is [50, 48, 50, 49, 48, 49, 48, 49, 48, 49, 48, 49, 50, 48, 50, 49, 48, 49, 48, 49, 48, 49, 48, 49] which represents 20210101 01:01 20210101 01:01. You could in theory use Input Datetime but it will take too much time to develop. I'd rather use HA automation for this.

###Frost Protection (not implemeted)
For frost protection you would need to add another switch and a proper code + bus listener.

The implementation into source code is not the problem, what I meant is the behavior. When I activate frost protection the TRV publishes following:

front protection = on
target temp = 8
mode = schedule

which is misinterpreted by HA fronted climate component. This is what I meant. It should display in HA frontend that the heating is off and the input_boolean front protection is active.

If looking in the commit for the first added  tuya TRV presets its looks being easy (if not need adding tests) more presets in ZHA climate component.
https://github.com/home-assistant/core/pull/48178/files
I think one Holiday for this and one FI for Site can being good but if its possible making them not possible to select but is showing in the GUI and having one witch on the device card and with date and time for the holiday mode .
Then if setting one holiday date on the device card is ZHA shoeing holiday but cant changing it = OK then it must being cancelled in the device card.
The same with the FI cant being sett in ZHA GUI but with commands from cluster or switch on the device card and the user can see that the device is in that mode.

If you have frost protection then heating isn't really off.  I don't care about this function, if someone does the code can be anytime changed.

Ah - and you can't use Input Datetime - it's not implemented in ZHA ;-) https://www.home-assistant.io/integrations/zha/

There is currently support for the following device types within Home Assistant:
Alarm Control Panel
Binary Sensor
Climate (beta)
Cover
Fan
Light
Lock
Number (i.e. analog output)
Sensor
Switch

https://github.com/home-assistant/core/tree/dev/homeassistant/components/zha

Thats what I meant with:

You could in theory use Input Datetime but it will take too much time to develop. I'd rather use HA automation for this.

One could implement Input Datetime into ZHA, but not me :D
BTW. I'd rather invest the time into naming those entities like I mentioned here https://github.com/zigpy/zha-device-handlers/issues/1061#issuecomment-962846745. FYI I've raise an issue on zigpy, I'll overlook integration of description into onoff cluster.

I have been testing this and seems to work mostly ok (sometimes gets confused and stuck in "off" mode.
Anyone else noticed the valve changing climate setpoints by itself?
I have an automation set to send a '0' analog_output_temperature_offset every 15 mins to get the current temperature and the set point seems to jump back to 21°C randomly (not every request).

To be honest, I never installed this TRV, it was just sitting on my desk to development purposes 😄 But I've installed it today.
I'll try to investigate the changing climate setpoint, but can you elaborate what are your settings? Are you using Schedule mode or Manual? What are your automations?

I just left the valve in "🏠" (home mode) which I guess is schedule?
 Unfortunately, we cannot customize the schedule yet, but the manual mode is a good workaround

Currently working:
* ambient temperature is sent to HA

* setting a temperature is sent between devices vice-versa (independant of mode)

* off-mode and manual mode can be toggled

I think I have the same thermostat. Can you help me to get at least the temperature control working?
I sadly don't really  understand what device class and so on is.
Would be lovely if you could help me getting it to work :)

Sorry for not explaining myself very well in the last message.
I'm wondering how I can use the custom ZONNSMART quirk. Which steps should I take to activate it?

Is there anything left to do to get this into the next release?

I am also interested in this device support. just bought a few valves. thank you.

@rforro are you able to publish the quirk so the users could use it?

I was waiting if your PR will be accepted or you'll have to replace the Bus.

I think I have the same thermostat. Can you help me to get at least the temperature control working? I sadly don't really understand what device class and so on is. Would be lovely if you could help me getting it to work :)

@LennardPlay To get the valve partly working, I just:

downloaded the valve.zip file
uploaded the extracted contents of this zip file (valve.py) to /config/custon_zha_quirks/
added the following to configuration.yaml:

zha:
  custom_quirks_path: /config/custom_zha_quirks/

restarted home assistant

I haven't modified climate.py yet as I was worried about breaking things/ran out of time/it looked a bit more in depth

There is a small indentation error in https://github.com/zigpy/zha-device-handlers/issues/1027#issuecomment-962854799 @rforro
class ZONNSMARTThermostat(Thermostat):
    """ZONNSMART Thermostat implementation"""
    def __init__(self, unique_id, zha_device, channels, **kwargs):
        """Initialize ZHA Thermostat instance."""
        super().__init__(unique_id, zha_device, channels, **kwargs)
            self._presets = [
            PRESET_SCHEDULE,

should instead be:
class ZONNSMARTThermostat(Thermostat):
    """ZONNSMART Thermostat implementation"""
    def __init__(self, unique_id, zha_device, channels, **kwargs):
        """Initialize ZHA Thermostat instance."""
        super().__init__(unique_id, zha_device, channels, **kwargs)
        self._presets = [
            PRESET_SCHEDULE,

self._presets line changed

I'm working on this to include boost and anti-freeze mode, but there is one thing which won't let me sleep.
2021-11-04 19:27:47 DEBUG (MainThread) [zhaquirks.tuya] [0xb5eb:1:0xef00] Received value [1] for attribute 0x0473 (command 0x0001)

There is this ONLINE datapoint which publishes value 1 at pairing only. Now I understand its purpose. Using original Tuya App or Zigbee2mqtt by publishing value 0 (boolean false) to this datapoint the TRV switches itself to "online mode" (antenna icon lights up) and for ca. 1 minute the TRV will be publishing all parameters including current room temperature automatically. The problem is for some reason I cannot publish the correct value (0 or false) which will be accepted by TRV from ZHA. I've tried t.Bool and t.uint8_t but the TRV just ignores the value and publishes some strange data:
2022-01-06 10:59:57 DEBUG (MainThread) [zigpy_znp.api] Received command: AF.IncomingMsg.Callback(GroupId=0x0000, ClusterId=61184, SrcAddr=0x59A9, SrcEndpoint=1, DstEndpoint=1, WasBroadcast=<Bool.false: 0>, LQI=115, SecurityUse=<Bool.false: 0>, TimeStamp=9468090, TSN=0, Data=b'\x0C\x02\x10\x18\x0B\x00\x00', MacSrcAddr=0x59A9, MsgResultRadius=29)
2022-01-06 10:59:57 DEBUG (MainThread) [zigpy.zcl] [0x59a9:1:0xef00] ZCL deserialize: <ZCLHeader frame_control=<FrameControl frame_type=GLOBAL_COMMAND manufacturer_specific=True is_reply=True disable_default_response=False> manufacturer=4098 tsn=24 command_id=Command.Default_Response>

Correct data for Online DP
2022-01-06 10:32:28 DEBUG (MainThread) [zigpy_znp.api] Received command: AF.IncomingMsg.Callback(GroupId=0x0000, ClusterId=61184, SrcAddr=0x59A9, SrcEndpoint=1, DstEndpoint=1, WasBroadcast=<Bool.false: 0>, LQI=110, SecurityUse=<Bool.false: 0>, TimeStamp=4312484, TSN=0, Data=b'\x09\x44\x01\x00\x71\x73\x04\x00\x01\x01', MacSrcAddr=0x59A9, MsgResultRadius=29)
2022-01-06 10:32:28 DEBUG (MainThread) [zigpy.zcl] [0x59a9:1:0xef00] ZCL deserialize: <ZCLHeader frame_control=<FrameControl frame_type=CLUSTER_COMMAND manufacturer_specific=False is_reply=True disable_default_response=False> manufacturer=None tsn=68 command_id=1>

Can some zigpy-pro dev point me into right direction?

If testing is needed: I have a 'TV02-ZG LED display on the side and rotating knob on the top.' as shown in https://github.com/zigpy/zigpy/discussions/653 and it would be nice if i could help. But i am standard user - no developer or professional in coding and implementing...

There is a new completely rewritten version, which will transform itself in following days into PR. I removed fault detection, because I cannot test this functionality, but add Frost Protection mode and Boost mode.
This version has:

heating operation can be off or heat
presets to choose from manual/schedule/holiday/frost protection
binary sensor to show when opened window is detected
analogue input to set temperature when opened window detected
analogue input to set temperature offset
switch for child lock
switch to enable boost mode for 5min

Quirk is here ts0601_trv.zip and don't forget to add into /components/zha/climate.py following lines:
@STRICT_MATCH(
    channel_names=CHANNEL_THERMOSTAT,
    manufacturers={
        "_TZE200_hue3yfsn",
        },
)

class ZONNSMARTThermostat(Thermostat):
    """ZONNSMART Thermostat implementation"""

    PRESET_HOLIDAY = "holiday"
    PRESET_FROST = "frost protect"

    def __init__(self, unique_id, zha_device, channels, **kwargs):
        """Initialize ZHA Thermostat instance."""
        super().__init__(unique_id, zha_device, channels, **kwargs)
            self._presets = [
                PRESET_NONE,
                self.PRESET_HOLIDAY,
                PRESET_SCHEDULE,
                self.PRESET_FROST,
        ]
        self._supported_flags |= SUPPORT_PRESET_MODE

    async def async_attribute_updated(self, record):
        """Handle attribute update from device."""
        if record.attr_name == "operation_preset":
            if record.value == 0:
                self._preset = PRESET_SCHEDULE
            if record.value == 1:
                self._preset = PRESET_NONE
            if record.value == 3:
                self._preset = self.PRESET_HOLIDAY
            if record.value == 4:
                self._preset = self.PRESET_FROST
        await super().async_attribute_updated(record)

    async def async_preset_handler(self, preset: str, enable: bool = False) -> bool:
        """Set the preset mode."""
        mfg_code = self._zha_device.manufacturer_code
        if not enable:
            return await self._thrm.write_attributes(
                {"operation_preset": 1}, manufacturer=mfg_code
            )
        if preset == PRESET_SCHEDULE:
            return await self._thrm.write_attributes(
                {"operation_preset": 0}, manufacturer=mfg_code
            )
        if preset == self.PRESET_HOLIDAY:
            return await self._thrm.write_attributes(
                {"operation_preset": 3}, manufacturer=mfg_code
            )
        if preset == self.PRESET_FROST:
            return await self._thrm.write_attributes(
                {"operation_preset": 4}, manufacturer=mfg_code
            )
        return False

That was quick. I would like to test, but i couldnt find the file climate.py. I also didnt find the directory /components/zha on my raspi (Home-Assistant core-2021.12.8 supervisor-2021.12.2 Home Assistant OS 7.1)

That was quick. I would like to test, but i couldnt find the file climate.py. I also didnt find the directory /components/zha on my raspi (tried to find it via terminal an via HomeAssistant-file-editor: the highest directory there is /config/

I have the same device so it looks like same as mine HA.
The one off_off is child lock and the other one is Boost mode, there is no possibility to pass the name to HA Frontend so you have to test it and rename it by yourself. The binary_input says if an opened window was detected or not.
As for the climate.py you cannot find it, because its inside of an docker container. You have to login into a shell inside of the homeassistant docker container and then you can access the climate.py file.

Thank you very much. With these informations i was able to identify some functions and rename the equivalent pieces:

The 'climaty.py'-point must wait (at least until tomorrow), as it seams to work fundamentally until here...

As for the climate.py you cannot find it, because its inside of an docker container. You have to login into a shell inside of the homeassistant docker container and then you can access the climate.py file.

I did ssh on my HomeAssistant-Pi (via terminal from my pc) and the only things with 'climate' i found was /root/.oh-my-zsh/plugins/codeclimate/ but no climate.py in there.
The shell inside HomeAssistant (via SSH & Web Terminal -addon version: 10.0.1) also doesnt find the mentioned directory /components/zha/ and the file climate.py.
I am running HomeAssistant OS, not in docker container. Maybe i am too nooby?

As for the climate.py you cannot find it, because its inside of an docker container. You have to login into a shell inside of the homeassistant docker container and then you can access the climate.py file.

I did ssh on my HomeAssistant-Pi (via terminal from my pc) and the only things with 'climate' i found was /root/.oh-my-zsh/plugins/codeclimate/ but no climate.py in there.
The shell inside HomeAssistant (via SSH & Web Terminal -addon version: 10.0.1) also doesnt find the mentioned directory /components/zha/ and the file climate.py.
I am running HomeAssistant OS, not in docker container. Maybe i am too nooby?

you can get the quirk to work by uploading the contents of the zip file to home assistant, and then adding the following to configuration.yaml:
zha:
  custom_quirks_path: /config/custom_zha_quirks/

Accessing (updating) the files in the docker container is a little more complex (with increased risk of breaking your Home Assistant installation), you need to use the portainer add-on, see https://github.com/zigpy/zha-device-handlers#testing-quirks-in-development-in-docker-based-install

Ok, thanks again. But a "little" to complicated / risky for me. I am using docker + portainer on another machine, but for pi-hole only. So i will wait for the official release to have all this included and for now i let this until here functionally working with your zip-file and the 2 lines in the yaml. :)

https://github.com/zigpy/zha-device-handlers/issues/1027#issuecomment-1008433665

With these informations i was able to identify some functions and rename the equivalent pieces:
.... it seams to work fundamentally until here...

This looks great, better then the downloadable .py files I tried from this issue. Could you (Perrudi) share your file?

@rforro thanks for the work you put into this
For me the "Set Temperature" keeps resetting in HA but the TRV itself keeps the temperature.
I'll look into this a bit more once I have some more time.

#1027 (comment)

With these informations i was able to identify some functions and rename the equivalent pieces:
.... it seams to work fundamentally until here...

This looks great, better then the downloadable .py files I tried from this issue. Could you (Perrudi) share your file?

This is my file, same as shared a few posts above, unchanged (zipped to be able to post it here, no password):
valve.py.zip

I have the same TRV from AliExpress and it is working with the files from rforro (with the climate.py ident fix).
Thanks @rforro and @Perrudi.
Hope the PR comes soon and makes it to the master tree :)

In case anyone is stuck with don't forget to add into /components/zha/climate.py following lines from this comment, you can perform the following steps (if you know what you are doing):

Install the ssh addon: https://github.com/hassio-addons/addon-ssh
Disable protection mode from the addon UI and (re)start the addon
Open the ssh terminal and enter the following commands:

docker exec  -it homeassistant /bin/bash to connect to the home assistant docker container
find / -name "climate.py" | grep "components/zha/climate.py" to find the needed file, if you do not have exactly one line as output, something went wrong, e.g. you are not in the docker container
vi /usr/src/homeassistant/homeassistant/components/zha/climate.py to open the file in vim
SHIFT+G to go to the end of the file
I (big i) to switch to insert mode
CTRL+V to paste the following content (CAUTION, do not copy directly from the comment above as there are some minor formatting/indent errors which break your config!):

@STRICT_MATCH(
    channel_names=CHANNEL_THERMOSTAT,
    manufacturers={
        "_TZE200_hue3yfsn",
    },
)

class ZONNSMARTThermostat(Thermostat):
    """ZONNSMART Thermostat implementation"""

    PRESET_HOLIDAY = "holiday"
    PRESET_FROST = "frost protect"

    def __init__(self, unique_id, zha_device, channels, **kwargs):
        """Initialize ZHA Thermostat instance."""
        super().__init__(unique_id, zha_device, channels, **kwargs)
        self._presets = [
            PRESET_NONE,
            self.PRESET_HOLIDAY,
            PRESET_SCHEDULE,
            self.PRESET_FROST,
        ]
        self._supported_flags |= SUPPORT_PRESET_MODE

    async def async_attribute_updated(self, record):
        """Handle attribute update from device."""
        if record.attr_name == "operation_preset":
            if record.value == 0:
                self._preset = PRESET_SCHEDULE
            if record.value == 1:
                self._preset = PRESET_NONE
            if record.value == 3:
                self._preset = self.PRESET_HOLIDAY
            if record.value == 4:
                self._preset = self.PRESET_FROST
        await super().async_attribute_updated(record)

    async def async_preset_handler(self, preset: str, enable: bool = False) -> bool:
        """Set the preset mode."""
        mfg_code = self._zha_device.manufacturer_code
        if not enable:
            return await self._thrm.write_attributes(
                {"operation_preset": 1}, manufacturer=mfg_code
            )
        if preset == PRESET_SCHEDULE:
            return await self._thrm.write_attributes(
                {"operation_preset": 0}, manufacturer=mfg_code
            )
        if preset == self.PRESET_HOLIDAY:
            return await self._thrm.write_attributes(
                {"operation_preset": 3}, manufacturer=mfg_code
            )
        if preset == self.PRESET_FROST:
            return await self._thrm.write_attributes(
                {"operation_preset": 4}, manufacturer=mfg_code
            )
        return False

ESC to switch back to normal mode
:wq to write changes and quit vim
exit to exit the docker container

Enable protection mode in the ssh addon UI, (optionally) disable the addon
Restart home assistant
Profit

Some follow-up: If you are running Home Assistant as a container, you need to ssh into your machine and run the docker command with sudo. Everything in the instructions related to the addon can be ignored.

Ok, you warned us: '(if you know what you are doing)'
I am not used to VIM and all these bin-bash-things, but i want to help to bring this forward. So joking aside, gone through step by step and obviously worked. Only at ':wq' I stumbled, but with ESC then single :w (write?) and :q (quit?) I guess it worked. Restarted HA and it is back as before. I will try to see, if anything in lovelace or behavior of the 'thermostat-card' changed.
Thank you.

Thanks @rforro for providing the files. I tested the setup today and can confirm that it almost works perfectly. The only thing that seems broken is the current temperature listed in climate.tze200_hue3yfsn_ts0601_63162ffe_thermostat. It is set when first connecting the thermostat to HA but never updates after that. The heating regulation is not effected and works as intended, so I think that the updated value is simply not sent to HA.
Does anyone else also have this issue/is this a known problem?

Thanks @rforro for providing the files. I tested the setup today and can confirm that it almost works perfectly. The only thing that seems broken is the current temperature listed in climate.tze200_hue3yfsn_ts0601_63162ffe_thermostat. It is set when first connecting the thermostat to HA but never updates after that. The heating regulation is not effected and works as intended, so I think that the updated value is simply not sent to HA.
Does anyone else also have this issue/is this a known problem?

known issue, see here for explanation
and first example here for a work-around in home assistant

The new code is running well with Homeassistant 2022.02.09.
Thanks @rforro

Hello guys, I have same SMART THERMOSTAT (TV02 Zigbee) mentioned in the beginning. But I am beginner in all this stuff around HA and implementations. Is there anybody who is able to help me step by step with this. I will really appreciate it. THANK YOU SO MUCH FOR YOUR HELP

It's all mentioned above. Short version: Take the last ts0601_trv.zip and put it into homeassistant (in homeassistant included file-editor) and do the steps done in the posts above: https://github.com/zigpy/zha-device-handlers/issues/1027#issuecomment-1008350291 and https://github.com/zigpy/zha-device-handlers/issues/1027#issuecomment-1030847151
Or describe the specific step, you are stuck in.

Hello guys, I have same SMART THERMOSTAT (TV02 Zigbee) mentioned in the beginning. But I am beginner in all this stuff around HA and implementations. Is there anybody who is able to help me step by step with this. I will really appreciate it. THANK YOU SO MUCH FOR YOUR HELP

Just wait a month. This code was already merged and soon will be included in one of next releases of HA. Probably not in March but April for sure.

I have this device https://aliexpress.com/item/1005003172662104.html, the manual says it is a TV02 Zigbee Thermostat Radiator Valve, but I can't get it to pair via zigbee2mqtt 1.23.0 (other devices, i.e. switches do work). Why would it work via this method?
The unit is sold as if it only works with a Tuya gateway. Is that the case?  If pairing should always work, perhaps the hardware is just broken.

This quirk has made it into 2022.03 so you don't need to create custom_quirks anymore. But it's not all roses yet, present are still waiting for its release and I think it will be 2022.04

Version 2022.03...Now I Can see my thermostat, actual temperature is ok,but wanted temperatures is 5time bigger...eg. 110 is like 22°C. Thank you for your help.

Version 2022.03...Now I Can see my thermostat, actual temperature is ok,but wanted temperatures is 5time bigger...eg. 110 is like 22°C. Thank you for your help.

Can you post some printscreens and as well make a photo of your TRV please.

I'm suspecting, that your TRV has newer Firmware, which is not good. Two things. Please make one more screenshot in Configuration -> Devices & Services -> ZHA -> _TZE200_hue3yfsn TS0601 -> Manage Cluster (under device info) -> Clusters -> ZONNSMARTManufCluster -> Cluster Attributes -> target_temperature -> Get Zigbee Attribute. If you set the temperature on TRV to 22.0 it should show 220 value (yours will be probably different)
Post aliexpress link to the device which one you bought, no similar. It has to be the same thing, because I'll buy it as well.

aliexpress is exactly THE LINK, where did I buy it.
I've got no ZHA. It is tuya integration through zigbee gateway.
But look at this.

{
"home_assistant": {
"installation_type": "Home Assistant OS",
"version": "2022.3.1",
"dev": false,
"hassio": true,
"virtualenv": false,
"python_version": "3.9.9",
"docker": true,
"arch": "armv7l",
"timezone": "Europe/Prague",
"os_name": "Linux",
"os_version": "5.10.92-v7",
"supervisor": "2022.02.dev1701",
"host_os": "Home Assistant OS 7.4",
"docker_version": "20.10.9",
"chassis": "embedded",
"run_as_root": true
},
"custom_components": {
"rpi_rf": {
"version": "2022.2.9",
"requirements": [
"rpi-rf==0.9.7",
"RPi.GPIO==0.7.1"
]
},
"localtuya": {
"version": "3.2.1",
"requirements": []
},
"xiaomi_miot": {
"version": "0.5.3",
"requirements": [
"construct==2.10.56",
"python-miio>=0.5.6",
"micloud>=0.3"
]
},
"hacs": {
"version": "1.23.0",
"requirements": [
"aiogithubapi>=21.11.0"
]
},
"smartthinq_sensors": {
"version": "0.12.10",
"requirements": [
"pycountry>=20.7.3"
]
}
},
"integration_manifest": {
"domain": "tuya",
"name": "Tuya",
"documentation": "https://www.home-assistant.io/integrations/tuya",
"requirements": [
"tuya-iot-py-sdk==0.6.6"
],
"dependencies": [
"ffmpeg"
],
"codeowners": [
"@Tuya",
"@zlinoliver",
"@METISU",
"@frenck"
],
"config_flow": true,
"iot_class": "cloud_push",
"dhcp": [
{
"macaddress": "105A17*"
},
{
"macaddress": "10D561*"
},
{
"macaddress": "1869D8*"
},
{
"macaddress": "381F8D*"
},
{
"macaddress": "508A06*"
},
{
"macaddress": "68572D*"
},
{
"macaddress": "708976*"
},
{
"macaddress": "7CF666*"
},
{
"macaddress": "84E342*"
},
{
"macaddress": "D4A651*"
},
{
"macaddress": "D81F12*"
}
],
"loggers": [
"tuya_iot"
],
"is_built_in": true
},
"data": {
"endpoint": "https://openapi.tuyaeu.com",
"auth_type": 0,
"country_code": "420",
"app_type": "smartlife",
"mqtt_connected": true,
"disabled_by": null,
"disabled_polling": false,
"name": "Living room",
"model": "",
"category": "wkf",
"product_id": "hue3yfsn",
"product_name": "TV02-ZG",
"online": true,
"sub": true,
"time_zone": "+02:00",
"active_time": "2021-10-13T12:24:27+00:00",
"create_time": "2021-10-13T12:24:27+00:00",
"update_time": "2022-01-20T14:26:53+00:00",
"function": {
"mode": {
"type": "Enum",
"value": {
"range": [
"auto",
"manual",
"holiday"
]
}
},
"window_check": {
"type": "Boolean",
"value": {}
},
"temp_set": {
"type": "Integer",
"value": {
"unit": "\u2103",
"min": 50,
"max": 300,
"scale": 1,
"step": 5
}
},
"holiday_temp_set": {
"type": "Integer",
"value": {
"unit": "\u2103",
"min": 50,
"max": 300,
"scale": 1,
"step": 5
}
},
"child_lock": {
"type": "Boolean",
"value": {}
}
},
"status_range": {
"mode": {
"type": "Enum",
"value": {
"range": [
"auto",
"manual",
"holiday"
]
}
},
"window_check": {
"type": "Boolean",
"value": {}
},
"temp_set": {
"type": "Integer",
"value": {
"unit": "\u2103",
"min": 50,
"max": 300,
"scale": 1,
"step": 5
}
},
"temp_current": {
"type": "Integer",
"value": {
"unit": "\u2103",
"min": -200,
"max": 500,
"scale": 1,
"step": 1
}
},
"holiday_temp_set": {
"type": "Integer",
"value": {
"unit": "\u2103",
"min": 50,
"max": 300,
"scale": 1,
"step": 5
}
},
"battery_percentage": {
"type": "Integer",
"value": {
"unit": "%",
"min": 0,
"max": 100,
"scale": 0,
"step": 1
}
},
"child_lock": {
"type": "Boolean",
"value": {}
}
},
"status": {
"mode": "holiday",
"window_check": false,
"temp_set": 170,
"temp_current": 186,
"holiday_temp_set": 170,
"battery_percentage": 100,
"child_lock": false
},
"home_assistant": {
"name": "Living room",
"name_by_user": "Termostat - ob\u00fdv\u00e1k",
"disabled": false,
"disabled_by": null,
"entities": [
{
"disabled": false,
"disabled_by": null,
"entity_category": "diagnostic",
"device_class": null,
"original_device_class": "battery",
"icon": null,
"original_icon": null,
"unit_of_measurement": "%",
"state": {
"entity_id": "sensor.living_room_battery",
"state": "100.0",
"attributes": {
"state_class": "measurement",
"unit_of_measurement": "%",
"device_class": "battery",
"friendly_name": "Living room Battery"
},
"last_changed": "2022-03-07T09:37:32.402475+00:00",
"last_updated": "2022-03-07T09:37:32.402475+00:00"
}
},
{
"disabled": false,
"disabled_by": null,
"entity_category": "config",
"device_class": null,
"original_device_class": null,
"icon": null,
"original_icon": "mdi:account-lock",
"unit_of_measurement": null,
"state": {
"entity_id": "switch.living_room_child_lock",
"state": "off",
"attributes": {
"icon": "mdi:account-lock",
"friendly_name": "Living room Child Lock"
},
"last_changed": "2022-03-05T12:17:14.849946+00:00",
"last_updated": "2022-03-05T12:17:14.849946+00:00"
}
},
{
"disabled": false,
"disabled_by": null,
"entity_category": "config",
"device_class": null,
"original_device_class": null,
"icon": null,
"original_icon": "mdi:window-open",
"unit_of_measurement": null,
"state": {
"entity_id": "switch.living_room_open_window_detection",
"state": "off",
"attributes": {
"icon": "mdi:window-open",
"friendly_name": "Living room Open Window Detection"
},
"last_changed": "2022-03-05T12:17:14.854961+00:00",
"last_updated": "2022-03-05T12:17:14.854961+00:00"
}
},
{
"disabled": false,
"disabled_by": null,
"entity_category": null,
"device_class": null,
"original_device_class": null,
"icon": null,
"original_icon": null,
"unit_of_measurement": null,
"state": {
"entity_id": "climate.living_room",
"state": "heat_cool",
"attributes": {
"hvac_modes": [
"off",
"heat_cool",
"heat_cool"
],
"min_temp": 25.0,
"max_temp": 150.0,
"target_temp_step": 0.5,
"current_temperature": 18.6,
"temperature": 110.0,
"friendly_name": "Living room",
"supported_features": 1
},
"last_changed": "2022-03-06T18:48:23.258890+00:00",
"last_updated": "2022-03-07T17:30:01.676699+00:00"
}
}
]
}
}
}

2. I've got no ZHA. It is tuya integration through zigbee gateway.

That's the problem! This code is for ZHA integration only, no Tuya. You should look here https://github.com/home-assistant/core/issues?q=is%3Aissue+is%3Aopen+label%3A"integration%3A+tuya"

OH...thank you and sorry for my mistake. But before 2022.03 version, I couldn't see or set nothing on my thermostats so for now,it is still small win ...

I updated my HA to 2022.3.3 today and added this device via ZHA.
Unfortunately, I noticed that the actual temperature is not updating. It sticks to the value it had at TRV start and does not change. Removing the battery and inserting it again sets a single new value but nothing more after that.
Apart from that the other values seem to work correctly.
Is this a known problem? Or is the TRV behaving strangely?
Does it make sense to post device data and logs?

You shold read this whole issue. It is know behaviour.
TLDR
This TRV saves energy and transmits data only when it is absolutely neccesary, unless you turn the "online mode" on. In this case the TRV will be for ca. 1 minute publishing all values inclusive current temperature. Look for those 3 on_off switches in zha, one is in default state on. This is the online mode. Turn it off and your device will be in online mode, in this case the antenna icon on TRV will light up. You can create automation which will turn the online mode periodically.

With an automaton activating the trigger, it works fine now.
Thanks for for taking the time to write a quick summary and many thanks for you efforts of integrating that device. I really appreciate it!

My TRV is consuming a set of batteries per couple of weeks, even though I have the online mode off.
Is anyone having a similar issue?

This is the online mode. Turn it off and your device will be in online mode,

Please correct this sentence and make less mistakes when writing, if possible.

My TRV is consuming a set of batteries per couple of weeks, even though I have the online mode off. Is anyone having a similar issue?

I expect that most of the energy is going towards mechanical actions. If you are going on and off all day long, it's probably going faster.
There is no percentage battery indicator, is there? In that case, perhaps mine will also fail in a few days. I have online still on and didn't implement the optimizations yet.

@MattWestb I've modified Zonnsmart entry for your Tuya TRV Matrix, you can just copy paste it from here:
Zonnsmart and Co

Design:

TV01-ZG Squerich with monochrome LCD and buttons on flat upper side.
TV02-ZG LED display on the side and rotating knob on the top.
TV05-ZG Rounded with LED display on the side and rotary knob on top.

Known behaviour
In order to save energy, this family of TRVs don't publishes room temperature unless it's requested. Use automation to activate online mode periodically. (online mode = on_off switch with reversed polarity)
Implemented functions:
Modes:

1 Scheduled/auto (set/report) ✅
2 Manual (set/report) ✅
3 Holiday is on (report only) ✅
4 Holiday show temperature (set/report) ✅

Reporting local temperature (by activating online state) ✅
Setting / reporting current setpoint temperature ✅
Setting / reporting opened window temperature ✅
Setting / reporting temperature offset ✅
Setting / reporting comfort temperature ☑
Setting / reporting eco temperature ☑
Setting / reporting stop heating ✅
Setting / reporting boost mode time ☑
Activating / deactivating boost mode ✅
Setting / reporting frost protection (as preset) ✅
Reporting uptime ⬜
Setting / reporting Schedule ⬜
Setting / reporting Begin and End of Holiday mode ⬜
Activating online state ✅
Setting / reporting child lock ✅
Setting / reporting window detection ✅
Reporting battery low / % ✅
ZHA support:
✅ Yes and verified,
☑ Yes but only through Manage Clusters,
⬜ Not implemented.
Known devices:
Zonnsmart is making different software IDs for some customers and some (Moes) have being seen  is using all IDs.

OEM / Brand
Model
Manufacturer Name
Model ID
ZHA Quirk
Request

Zonnsmart
TV01-ZG
_TZE200_e9ba97vf
TS0601
✅ ZS
983

Tesla
TSL-TRV-TV01ZG
_TZE200_husqqvux
TS0601
✅ ZS
1072

SHENZHEN RSH
TV02-ZG
_TZE200_hue3yfsn
TS0601
✅ ZS
1027 1381

EARU
TV05-ZG
_TZE200_kly8gjlz
TS0601
✅ ZS
1182

☑ = Not in dev and experimental in the device request.

@MattWestb perfect! Only small change in the known devices table. There is RV05-ZigBee = _TZE200_hue3yfsn but on tuya webpage this product is called TV02-ZG https://expo.tuya.com/product/947044 Same as in Design section.

Known devices:
Zonnsmart is making different software IDs for some customers and some (Moes) have being seen  is using all IDs.

OEM / Brand
Model
Manufacturer Name
Model ID
ZHA Quirk
Request

Zonnsmart
TV01-ZG
_TZE200_e9ba97vf
TS0601
✅ ZS
983

Tesla
TSL-TRV-TV01ZG
_TZE200_husqqvux
TS0601
✅ ZS
1072

Zonnsmart
TV02-ZG
_TZE200_hue3yfsn
TS0601
✅ ZS
1027 1381

EARU
TV05-ZG
_TZE200_kly8gjlz
TS0601
✅ ZS
1182

I was changing the manufacture name then rebranded is not interesting if not heaving unique device ID like Tesla is having (they looks having re-branding most tuya TRVs like MOES have doing) .
Expo tuya is coming and going with manufactures and re branded devices so not all time possible finding the manufacture for all devices.

Have founding 2 brands of the same TRV but i think the Zonnsmart is manufacture.
https://expo.tuya.com/product/857063 https://expo.tuya.com/product/947044.
Zonnsmart looks being one real manufacture but its not so important as long we is talking of the same device.
I think the naming Zonnsmart and Co is good for all this devices.

My TRV is consuming a set of batteries per couple of weeks, even though I have the online mode off. Is anyone having a similar issue?

The same is happening for me. I have a couple different TRVs and none of them is depleting this quickly. And the other ones are constantly transmitting temperature changes not only when activating some "online mode".
Glad I'm not the only one with that problem, I guess I'll buy a different TRV to replace this one 😄

My TRV is consuming a set of batteries per couple of weeks, even though I have the online mode off. Is anyone having a similar issue?

The same is happening for me. I have a couple different TRVs and none of them are depleting this quickly. And the other ones are constantly transmitting temperature changes not only when activating some "online mode". Glad I'm not the only one with that problem, I guess I'll buy a different TRV to replace this one 😄

It could be a battery type as well.  That means by using two fully charged rechargeable AA batteries the TRV will get only 2.5V which could be less that it expects (made in china).
This behavior was observed on some TRVs. I even saw some modifications, when users soldered a DC-DC step up voltage regulator to fix this issue.

@neurove the tuya TRVs is using one MCU for doing the TRV work and is only using the Zigbee module for tunneling the commands so we can configuring reporting and pulling in Zigbee network buts is not helping then the MCU is not listening on this commands = not working.
Using "online mode" all the time (24/7) is more then likely killing your battery fast so use it in one automation that is sending it every 10 minutes or so and between is off.
I have first gen TRVs (Siterwell) and after 18 mount 2 is on original batteries and 2 have getting one change and 1 have getting 2 new battery sets.

Hi guys,  may I have a question? Why I can see correct current temperature
in Celsius ( eg. 21°C) in thermostatic valve but my wanted temperature is
like 5 times more (eg showing 105 °C instead of 21).
Thank you
Dne út 29. 3. 2022 18:13 uživatel MattWestb @.***>
napsal:

@neurove https://github.com/neurove the tuya TRVs is using one MCU for
doing the TRV work and is only using the Zigbee module for tunneling the
commands so we can configuring reporting and pulling in Zigbee network buts
is not helping then the MCU is not listening on this commands = not working.
Using "online mode" all the time (24/7) is more then likely killing your
battery fast so use it in one automation that is sending it every 10
minutes or so and between is off.
I have first gen TRVs (Siterwell) and after 18 mount 2 is on original
batteries and 2 have getting one change and 1 have getting 2 new battery
sets.
—
Reply to this email directly, view it on GitHub
https://github.com/zigpy/zha-device-handlers/issues/1027#issuecomment-1082079367,
or unsubscribe
https://github.com/notifications/unsubscribe-auth/AX3VDUQG42HCHAJ6EKWWIRDVCMT27ANCNFSM5DVJEI6A
.
You are receiving this because you commented.Message ID:
@.***>

@neurove the tuya TRVs is using one MCU for doing the TRV work and is only using the Zigbee module for tunneling the commands so we can configuring reporting and pulling in Zigbee network buts is not helping then the MCU is not listening on this commands = not working. Using "online mode" all the time (24/7) is more then likely killing your battery fast so use it in one automation that is sending it every 10 minutes or so and between is off.
I have first gen TRVs (Siterwell) and after 18 mount 2 is on original batteries and 2 have getting one change and 1 have getting 2 new battery sets.

I had online mode off. I did have an automation in homeassistant that changed the temperature a few times per day.
The automation is still ongoing with the other TRV. I have now the two Zonnsmart TRVs off (didnt change the battery).
Is thee any way I could help debug the issue?

@davidmehren, @noantiq, @InnayTool, @Eisfunke, and @rforro: go harass someone else.

Has anyone seen the Tuya TV02 valve fully close? If so, does it require special installation?

@21stce Your device is one Thermostat Radiator Valve (TRV) that is made for regulating the flow of heating water for getting the room temperature to the stetted temperature and its using advance algorithms for doing that.
Most (not all) tuya TRVs dont have one off working mode instead one anti-freeze or away mode and is always "living".
If you device have on/off function and using it you is braking the calibration and its takes days for getting it working OK with the parameters of the room it shall heating.
Setting one very low setpoint temperature is the normal way if the device is not having anti-freeze or away mode (some is displaying off if min temp is stetted and on then max temp is stetted) and is working as it was off but is still having anti-freeze function activated.
If you like having one On / Off valve you have baying the wrong  type of device.
By the way keep personal thinking of other users and devs away from this forum than all is doing there work on there free time then its one community project or you is not getting any help then (if) you is needing it.

I dont knowing the device then i have others tuya TRVs that is always working well in the background as-long not valves is being jammed.
The frost protection is very likely not possible disabling with commands then its one safety future and can being enforced by regulations im many country.
Easiest way if you cant finding some one have writing of it is testing putting  the device in the freezer.
I think the old normal HY368 is having one "real" on / off mode https://zigbee.blakadder.com/Hysen_HY368.html but i dont knowing  how the anti frost is working on them.
I have helping the devs for most tuya TRVs implanting and testing fictionsin ZHA so have some knowledge how tuya have making things and how they is working in real but its not the same as have develop the device for tuya.
The ground is all tuya TRVs working the same way but have making different functions for them working as the company like them working in there system and we can changing the firmware in the device for getting them working in other ways we like (but some user is trying with mixed resolute).

Easiest way if you cant finding some one have writing of it is testing putting the device in the freezer.

You also need to have a piece of pipe to mount it to.

The frost protection is very likely not possible disabling with commands then its one safety future and can being enforced by regulations im many country.

I am seeing that it is "false", then what else is the point of such a switch, if it doesn't work? Also, I doubt that there are regulations for closing a valve when it is 19 degrees Celsius.

Can you explaining way you need pipe in the in the freezer ?
We have testing many tuya TRVs window open alarm  and antifreeze function this way and its working great without doing plumbings and only looking what commands its sending.
Most tuya TRV have antifreeze set to 5°C and not 19 degrees Celsius then its not danger at this temperature.

Literally the only way for it to pair is if it is on a piece of pipe. Otherwise, it refuses to pair. Perhaps you are saying that after you remove it, it does still work. I don't know whether it does that for a fact. That would possibly simplify things, but since you don't have this exact same device, it appears that you would not be able to say anything conclusive.

Can't someone build an open-source TRV that does something useful? I am in the market for twenty of those.

Then i dont have the knowledge of coding that you is having i think its the best you is writing one new firmware for your device MCU that i think (=not knowing) is one STM32 chip and implanting all function you need in your system.

@rforro  RE: your reply on the 9th Jan.
I've copied your ts0601_trv.zip and updated the climate.py as you suggested, but am getting the error message below when I restart HA.
Logger: homeassistant.config_entries
Source: custom_zha_quirks/ts0601_trv.py:52
First occurred: 3:41:49 PM (1 occurrences)
Last logged: 3:41:49 PM
Error setting up entry ConBee II - /dev/ttyACM0, s/n: DE2497749 - dresden elektronik ingenieurtechnik GmbH - 1CF1:0030 for zha
Traceback (most recent call last):
File "/usr/src/homeassistant/homeassistant/config_entries.py", line 335, in async_setup
result = await component.async_setup_entry(hass, self)
File "/usr/src/homeassistant/homeassistant/components/zha/init.py", line 99, in async_setup_entry
setup_quirks(config)
File "/usr/local/lib/python3.9/site-packages/zhaquirks/init.py", line 409, in setup
importer.find_module(modname).load_module(modname)
File "", line 529, in _check_name_wrapper
File "", line 1029, in load_module
File "", line 854, in load_module
File "", line 274, in _load_module_shim
File "", line 711, in _load
File "", line 680, in _load_unlocked
File "", line 850, in exec_module
File "", line 228, in _call_with_frames_removed
File "/config/custom_zha_quirks/ts0601_trv.py", line 52, in
class SiterwellManufCluster(TuyaManufClusterAttributes):
File "/usr/local/lib/python3.9/site-packages/zigpy/zcl/init.py", line 91, in init_subclass
raise TypeError(
TypeError: manufacturer_attributes is deprecated. Copy the parent class's attributes dictionary and update it with your manufacturer-specific attributes. Make sure to specify that it is manufacturer-specific through the  appropriate constructor or tuple!
Has anything changed recently to deprecate this?
How do I fix this?
Ps.
My TS0601 has a manufacture of _TZE200_lllliz3p.   Another one to add to the list.

Don't use this code, it was already merged and since then it was modified to be complaint with newer zigpy version. Take the code from dev branch

@rforro Many thx for your help. I have finally got it working.
Solution: (if anyone else is interested)
The TS0601_trv.py requires the manufacture ID of my devices to be included as follows :
MODELS_INFO: [
("_TZE200_e9ba97vf", "TS0601"),
("_TZE200_husqqvux", "TS0601"),
("_TZE200_kly8gjlz", "TS0601"),
("_TZE200_hue3yfsn", "TS0601"),  # TV02-ZG
("_TZE200_lllliz3p", "TS0601"),                             <<<=== My Device
Since I can not access these files directly ( I believe SSH to HA CLI is already inside a docker container) I found a workaround.
Workaround:
I copied the latest ts0601_trv.py code from the DEV branch and deployed it into the custom_zha_quirks folder and edited it from there.  A restart of HA Core seemed to fix it.  I can now manage this device.
Can this MAN ID be added to the MODEL_INFO for the next release.

@rforro
Now for another issue.    I would like to be able to change the temperature 'set point' on the TRV from HA.  The TRV entity for the thermostat has an attribute of 'temperature' which shows the 'set point'.
The plan is to have a HA Slider that can vary this 'set point' from the HA UI, but how can I send the value to the TRV.   An automation, triggered by the Slider change only permits me to send a fixed value, not the value of the slider.
Any suggestions as to how I can do this, please, would be appreciated.

@kevintedder You also need adding your new device ID in climate.py in the ZHA container for getting the presets working OK in HA:
https://github.com/home-assistant/core/blob/76d105d0ba2f6235acc9bebd21cc3cdf57073316/homeassistant/components/zha/climate.py#L766-L774 It can not being done with local quirk and you must doing it with SSH if you is running HA OS or portatiner if you have access to it in your system.
Do you have one name and model for your new device ?
I was adding it in our tuya TRV matrix but dont have any name for it. https://github.com/zigpy/zigpy/discussions/653#

For doing automation you can using Developer Tools -> Climate: Set temperature and putting in your device the temperature you like setting on your device.

I've tried this, but can only set a hardcoded value. I would like to use the value set by the slider.
Using a value of {{ state.input_number.slider }} gets rejected by YAML.

Then you need learning how to using the slider for sending the information to the climatic service in your automation.

I need some help if possible?
i just got in two of these devices
Zonnsmart | TV01-ZG | _TZE200_e9ba97vf | TS0601 |
After reading this thread i created a automation to switch "switch 3" on and of every few min and one TRV is nicely showing the current temperature the other one is always stuck at the starting temperature?
I have no clue why 1 is working perfect and the other is not? all other functions work perfectly.
any help would be really appreciated

@copywizard I too had many issues with similar TRVs.  Try connecting them via a hub directly to TUYA. It will offer a software update if one is available.  Mine worked so much better afterwards.
IMHO these devices are cheap and you get what you pay for.  After months of work trying different setups, I've manage to get them to control my heating as I want.
Is IOT ready yet for a full deployment? I don't think so. There are still too many differing standards. I'm waiting until the industry has agreed on just one for all to follow.  That may be a few more years yet.

I need some help if possible?
i just got in two of these devices
Zonnsmart | TV01-ZG | _TZE200_e9ba97vf | TS0601 |
After reading this thread i created a automation to switch "switch 3" on and of every few min and one TRV is nicely showing the current temperature the other one is always stuck at the starting temperature?
I have no clue why 1 is working perfect and the other is not? all other functions work perfectly.
any help would be really appreciated
you can ignore this i fixed my issue using this automation to trigger every now and then:
https://community.home-assistant.io/t/moes-tv01-trv-temp-sensor-issues/356903/4

For 100% percent last paired TRV works properly.
Someone took my coding approach xxxManuClusterSelf, but from early test stages.
    def __init__(self, *args, **kwargs):
        """Init."""
        super().__init__(*args, **kwargs)
        global ZonnsmartManuClusterSelf
        ZonnsmartManuClusterSelf = self

In init function ZonnsmartManuClusterSelf gets TRV self, but every next TRV overwrites ZonnsmartManuClusterSelf with own self.
That's why only last TRV will get commands.
Repaired approach should be like on my other TRV quirks.
ZONNSMARTManufClusterSelf = {}
...
    def __init__(self, *args, **kwargs):
        """Init."""
        super().__init__(*args, **kwargs)
        self.endpoint.device.ZONNSMARTManufCluster_bus.add_listener(self)
        global ZONNSMARTManufClusterSelf
        ZONNSMARTManufClusterSelf[self.endpoint.device.ieee] = self

and
    async def write_attributes(self, attributes, manufacturer=None):
        """Modify value before passing it to the set_data tuya command."""
        for attrid, value in attributes.items():
            if isinstance(attrid, str):
                attrid = self.attributes_by_name[attrid].id
            if attrid not in self.attributes:
                self.error("%d is not a valid attribute id", attrid)
                continue
            self._update_attribute(attrid, value)

            # different Endpoint for compatibility issue
            await ZonnsmartManuClusterSelf.endpoint.tuya_manufacturer.write_attributes(
                {ZONNSMART_OPENED_WINDOW_TEMP: value * 10}, manufacturer=None
            )
        return ([foundation.WriteAttributesStatusRecord(foundation.Status.SUCCESS)],)

changed to:
    async def write_attributes(self, attributes, manufacturer=None):
        """Modify value before passing it to the set_data tuya command."""
        for attrid, value in attributes.items():
            if isinstance(attrid, str):
                attrid = self.attributes_by_name[attrid].id
            if attrid not in self.attributes:
                self.error("%d is not a valid attribute id", attrid)
                continue
            self._update_attribute(attrid, value)

            # different Endpoint for compatibility issue
            await ZonnsmartManuClusterSelf[
                self.endpoint.device.ieee
            ].endpoint.tuya_manufacturer.write_attributes(
                {ZONNSMART_OPENED_WINDOW_TEMP: value * 10}, manufacturer=None
            )
        return ([foundation.WriteAttributesStatusRecord(foundation.Status.SUCCESS)],)

You automation trigger calls TRV by the IEEE address, that's why that exact TRV gets the command properly.
There are more bugs I see in dev
    attributes = TuyaManufClusterAttributes.attributes.copy()
    attributes = {
        ZONNSMART_MODE_ATTR: ("mode", t.uint8_t, True),
        ZONNSMART_WINDOW_DETECT_ATTR: ("window_detection", t.uint8_t, True),
        ZONNSMART_FROST_PROTECT_ATTR: ("frost_protection", t.uint8_t, True),
        ZONNSMART_TARGET_TEMP_ATTR: ("target_temperature", t.uint32_t, True),
        ZONNSMART_TEMPERATURE_ATTR: ("temperature", t.uint32_t, True),
        ZONNSMART_TEMPERATURE_CALIBRATION_ATTR: (
            "temperature_calibration",
            t.int32s,
            True,
        ),
        ZONNSMART_WEEK_FORMAT_ATTR: ("week_format", t.uint8_t, True),
        ZONNSMART_HOLIDAY_TEMP_ATTR: ("holiday_temperature", t.uint32_t, True),
        ZONNSMART_BATTERY_ATTR: ("battery", t.uint32_t, True),
        ZONNSMART_UPTIME_TIME_ATTR: ("uptime", t.uint32_t, True),
        ZONNSMART_CHILD_LOCK_ATTR: ("child_lock", t.uint8_t, True),
        ZONNSMART_FAULT_DETECTION_ATTR: ("fault_detected", t.uint8_t, True),
        ZONNSMART_BOOST_TIME_ATTR: ("boost_duration_seconds", t.uint32_t, True),
        ZONNSMART_OPENED_WINDOW_TEMP: ("opened_window_temperature", t.uint32_t, True),
        ZONNSMART_COMFORT_TEMP_ATTR: ("comfort_mode_temperature", t.uint32_t, True),
        ZONNSMART_ECO_TEMP_ATTR: ("eco_mode_temperature", t.uint32_t, True),
        ZONNSMART_HEATING_STOPPING_ATTR: ("heating_stop", t.uint8_t, True),
        ZONNSMART_ONLINE_MODE_BOOL_ATTR: ("online_set", t.uint8_t, True),
        ZONNSMART_ONLINE_MODE_ENUM_ATTR: ("online", t.uint8_t, True),
    }

should be changed to
    attributes = TuyaManufClusterAttributes.attributes.copy()
    attributes.update(
        {
            ZONNSMART_MODE_ATTR: ("mode", t.uint8_t, True),
            ZONNSMART_WINDOW_DETECT_ATTR: ("window_detection", t.uint8_t, True),
            ZONNSMART_FROST_PROTECT_ATTR: ("frost_protection", t.uint8_t, True),
            ZONNSMART_TARGET_TEMP_ATTR: ("target_temperature", t.uint32_t, True),
            ZONNSMART_TEMPERATURE_ATTR: ("temperature", t.uint32_t, True),
            ZONNSMART_TEMPERATURE_CALIBRATION_ATTR: (
                "temperature_calibration",
                t.int32s,
                True,
            ),
            ZONNSMART_WEEK_FORMAT_ATTR: ("week_format", t.uint8_t, True),
            ZONNSMART_HOLIDAY_TEMP_ATTR: ("holiday_temperature", t.uint32_t, True),
            ZONNSMART_BATTERY_ATTR: ("battery", t.uint32_t, True),
            ZONNSMART_UPTIME_TIME_ATTR: ("uptime", t.uint32_t, True),
            ZONNSMART_CHILD_LOCK_ATTR: ("child_lock", t.uint8_t, True),
            ZONNSMART_FAULT_DETECTION_ATTR: ("fault_detected", t.uint8_t, True),
            ZONNSMART_BOOST_TIME_ATTR: ("boost_duration_seconds", t.uint32_t, True),
            ZONNSMART_OPENED_WINDOW_TEMP: (
                "opened_window_temperature",
                t.uint32_t,
                True,
            ),
            ZONNSMART_COMFORT_TEMP_ATTR: ("comfort_mode_temperature", t.uint32_t, True),
            ZONNSMART_ECO_TEMP_ATTR: ("eco_mode_temperature", t.uint32_t, True),
            ZONNSMART_HEATING_STOPPING_ATTR: ("heating_stop", t.uint8_t, True),
            ZONNSMART_ONLINE_MODE_BOOL_ATTR: ("online_set", t.uint8_t, True),
            ZONNSMART_ONLINE_MODE_ENUM_ATTR: ("online", t.uint8_t, True),
        }
    )

And from what I see there is no code for HA -> TRV data sync back.
class ZONNSMARTThermostat(TuyaThermostatCluster):
Line:
https://github.com/zigpy/zha-device-handlers/blob/dev/zhaquirks/tuya/ts0601_trv.py#L1061
    DIRECT_MAPPING_ATTRS = {
        "occupied_heating_setpoint": (
            ZONNSMART_TARGET_TEMP_ATTR,
            lambda value: round(value / 10),
        ),
    }

should be changed to
    DIRECT_MAPPING_ATTRS = {
        "occupied_heating_setpoint": (
            ZONNSMART_TARGET_TEMP_ATTR,
            lambda value: round(value / 10),
        ),
        "local_temperature_calibration": (
            ZONNSMART_TEMPERATURE_CALIBRATION_ATTR,
            lambda value: round(value / 10),
        ),
    }

That's how when HA data of local_temperature_calibration are changed, they got synced back to TRV to the Zigbee TRV attribute 0x021B.
Off course calibration code line
https://github.com/zigpy/zha-device-handlers/blob/dev/zhaquirks/tuya/ts0601_trv.py#L1352
Should be changed to:
    async def write_attributes(self, attributes, manufacturer=None):
        """Modify value before passing it to the set_data tuya command."""
        for attrid, value in attributes.items():
            if isinstance(attrid, str):
                attrid = self.attributes_by_name[attrid].id
            if attrid not in self.attributes:
                self.error("%d is not a valid attribute id", attrid)
                continue
            self._update_attribute(attrid, value)

            await ZonnsmartManuClusterSelf[
                self.endpoint.device.ieee
            ].endpoint.tuya_manufacturer.write_attributes(
                {ZONNSMART_TEMPERATURE_CALIBRATION_ATTR: value * 10}, manufacturer=None
            )
        return ([foundation.WriteAttributesStatusRecord(foundation.Status.SUCCESS)],)

For anyone interested, I created a PR with the above fixes and scheduling support and more :
https://github.com/zigpy/zha-device-handlers/pull/1961
I believe the TRV is now fully supported, although I wish there was a better way to handle the schedules.

So creating a schedule is possible with ZHA? Can you send me a link to further information

See my PR   https://github.com/zigpy/zha-device-handlers/pull/1961 description. You need to fo go on the device page, and use Manage zigbee device from the device info box then update the attributes accordingly.

Thank you :) that helped a lot :)

I am using Home Assistant with conbee II and ZHA.
I have troubles controlling my TS0601 by _TZE200_hue3yfsn
Are the corrections already part of ZHA or do I have to add something manual to achieve the support for Tuya TV02?

I am using Home Assistant with conbee II and ZHA. I have troubles controlling my TS0601 by _TZE200_hue3yfsn Are the corrections already part of ZHA or do I have to add something manual to achieve the support for Tuya TV02?

I have troubles also. IN fact works better without the quirk but then some switchs ( child lock, open valve, etc) are mixed if you have more than 1 valve. Really strange.

With the quirk no even the switch are visible

You're posting to thread from year 2022 and write about using some quirk - which no one knows which you use.
So maybe try this one from my repo:
https://github.com/jacekk015/zha_quirks
ts0601_trv_zonnsmart.py

You're posting to thread from year 2022 and write about using some quirk - which no one knows which you use. So maybe try this one from my repo: https://github.com/jacekk015/zha_quirks ts0601_trv_zonnsmart.py

Man I tried you Zonnsmart.py, it works great, better than any other quirk.  The boost and child lock although are not directly auto detected it's a matter of testing them. Thanks a lot. Maybe you can add your quick to the main zha_device-handlerss repo branch.

The boost and child lock although are not directly auto detected it's a matter of testing them.
Not sure what do you mean by that.

Maybe you can add your quick to the main zha_device-handlerss repo branch.
I've tried once and failed. Will not try again.

The boost and child lock although are not directly auto detected it's a matter of testing them.

Not sure what do you mean by that.

Maybe you can add your quick to the main zha_device-handlerss repo branch.

I've tried once and failed. Will not try again.

1.- The switchs work but they are not properly identified as "child lock" and "boost", just as a generic switch. But it's fine.
2.- So sorry to heard it.
Have you got working preset modes (holiday, frost protect and scheduler) ?

There's no way to name a switch through quirk - unfortunately.

The boost and child lock although are not directly auto detected it's a matter of testing them. Only labeling is needed.

Not sure what do you mean by that.

Maybe you can add your quick to the main zha_device-handlerss repo branch.

I've tried once and failed. Will not try again.

1.- The switchs work but they are not properly identified as "child lock" and "boost", just as a generic switch. But it's fine. 2.- So sorry to heard it.
Have you got working preset modes (holiday, frost protect and scheduler) ?

Did you find a solution to get the name of the switches? I added now the quirk mentioned above and this did not solve it as mentioned by jacekk015. I have the TRV from Rollei.
TS0601
von _TZE200_hue3yfsn
Eigenart: ts0601_trv_zonnsmart.ZonnsmartTV01_ZG

Hi, I also have the TRV from Rollei.
The present modes are settable and visible.
For all the devices that I have:
switch => Boost mode
switch_2 => Child Lock
switch_3 => Unknown, maybe frost protection... sometimes it resets to true, sometimes not...
I have noticed that sometimes the TRV is not open the valve, if I set the temperature in the manuel heating mode to a target.
For example, the thermostat current room sensor shows 18 °C,  I set the TRV to 21°C and even after hours its not heating... The TRV shoes 21°C but it still not opens the valve... Sometimes it helps to turn off the heating and turn it on again, but sometimes this not works... @Panoramiac  you have same problems? Or for you it just works fine?
I never paired the TRVs with the Official App / Gateway... Im using the SkyConnector from nabu Casa...
someone found out what the "number.hermostat_nummer_opened_window_temperature" is doing?
Since today i also have the problem that the "Lock switch" on some TRVs stopped working... In HA it shows "True" but the TRV not activates the lock... But its not a network problem, when I change the temperature the TRV shows the new temperature directly...

@HoLy1337: "number.hermostat_nummer_opened_window_temperature" should be the temperature drop, when a window is open so that the TRV will close to save energy. I use Better Thermostat and external Window switches for that (I need to order some additional ones). My TRVs just arrived yesterday and I installed two of them. I did not really have time to install the remaining 6 (have 8). So no issues so far, but also not much experience ;-).  I would like to understand where in the ZHA files the names of these switches would be defined. I do not want to manually adjust the names for each TRV separately.  I use the Sonoff 3.0 Zigbee stick with ZHA. I saw yesterday a bug report with Better Thermostat and adjustment issues, have a look here: https://github.com/KartoffelToby/better_thermostat/issues/666

I would like to understand where in the ZHA files the names of these switches would be defined. I do not want to manually adjust the names for each TRV separately.

You will not find any place like that. It's just impossible as for ZHA now.
If you take a look at the OnOff ZCL cluster, there's no description field:
https://github.com/zigpy/zigpy/blob/dev/zigpy/zcl/clusters/general.py#L862

I've experienced better performance with the ts0601_trv_zonnsmart.py quirk in my setup. There are now two switches: "Switch Lock" for the child lock, and another named "Switch" for the 5-minute heating boost.
Additionally, I've made an improvement in my automation: the thermostat valve (TVR) now turns off when a window is opened, instead of just setting it to 5°C. This change isn't directly related to the quirk, but to my automation setup.
Also, I noticed that the Rolley TVR uses the "set_temperature" as an average temperature rather than as a minimum temperature.

Hi, I also have the TRV from Rollei. The present modes are settable and visible. For all the devices that I have: switch => Boost mode switch_2 => Child Lock switch_3 => Unknown, maybe frost protection... sometimes it resets to true, sometimes not...

The third one requests TRV to go into "Online mode" where it reports room temperautre. It has inverted state aka ON -> normal state, OFF -> requests online mode. Button will be better but at that time I wasn't available. And this functionality has a bug. If you have paired more than one TRV, only the last one reacts to this request.

FYI I've been working on this problem. Both #1961 and home-assistant/core#87546 are needed to solve the problem. The first one removes all the bogus fake clusters and implement scheduling support. The second one implement all the entities in HA with the correct names. Both are needed to make this work.

Nice to read that you are working on it. As I see you made already progress, I need to check the details and would be happy to support testing your changes ;-).
I have here currently the problem, that not all TRVs are getting their temperature update controlled by scheduler-component . Some TRVs stay then eg. at 20° instead of taking over the increase to 21.5° in the morning. I was using Better Thermostat, which currently makes a lot off issues with disabled BT devices, so I switched back to directly controlling the TRVs (still using the better thermostat widget). My daughter is complaining in the morning, that it is not warm enough in her room. I need to solve this soon ;-).

@Panoramiac HA debug logs could tell what's the problem with Better Thermostat. In other topic there were problem with enabling TRV's for which I've made a workaround in the quirk.
https://github.com/jacekk015/zha_quirks#in-case-of-errors-or-to-support-new-function


Cow: Watch dooflix.in

Cow requests the watch of the watch_keyword dooflix\.in. See the MS search here and the Stack Exchange search in text, in URLs, and in code.

dooflix\.in has been seen in 1 true positive, 0 false positives, and 0 NAAs.

Approved by double-beep in Charcoal HQ


Version 1.7.0

Codecov Report

Merging #155 into master will not change coverage.
The diff coverage is 100%.

@@          Coverage Diff          @@
##           master   #155   +/-   ##
=====================================
  Coverage     100%   100%
=====================================
  Files          21     22    +1
  Lines        1432   1484   +52
  Branches      192    206   +14
=====================================
+ Hits         1432   1484   +52

Impacted Files
Coverage Δ

src/util.ts
100% <100%> (ø)
:arrow_up:

src/third-party/EnsController.ts
100% <100%> (ø)

src/user/AddressBookController.ts
100% <100%> (ø)
:arrow_up:

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 8ae5ac3...b054cdc. Read the comment docs.


Option to redirect to stdout

Currently, I have to monkey patch it like this:
module ProgressClassMethods
  def io
    $stdout
  end
end
Progress.send(:extend, ProgressClassMethods)

Is there a way to override io method without monkey patching?

Currently there is no proper way, shorter way would be:
def Progress.io
  $stdout
end

But there can also be a feature to do it like:
Progress.io = $stdout

PR is welcome ;)

Implemented in b81054e02fb3a5ca1cbba544ed8c07e348c4494c and released in v3.3.0


Inline babel helpers rather than requiring them

This addresses https://github.com/OctoLinker/browser-extension/issues/351
by removing a couple of Function() calls from dist/app.js. Here's
the diff in the output of grep ' Function(' dist/app.js:
diff --git a/before.txt b/after.txt
index cfc9de2..c5c2ee1 100644
--- a/before.txt
+++ b/after.txt
@@ -1,4 +1,2 @@
-  ? window : typeof self != 'undefined' && self.Math == Math ? self : Function('return this')();
 	g = g || Function("return this")() || (1,eval)("this");
-      invoke(typeof fn == 'function' ? fn : Function(fn), args);
   ? window : typeof self != 'undefined' && self.Math == Math ? self : Function('return this')();

Hopefully, the remaining two calls will be ok, since they simply get the
global object, rather than have the potential to execute arbitrary code.
EDIT: See here for more info about the helpers option: https://github.com/babel/babel/tree/412180e20304347f8c402f7e3c0613951ac5144c/packages/babel-plugin-transform-runtime#helpers

Thanks for working with the review policies @josephfrazier !

Thank you, @Noitidart! For future reference, here is the Mozilla position on eval/Function, copied from our discussion on AMO:

Yes, it is ok to eval or new Function with static strings. So new Function('return this') is ok but let str = 'return this'; new Function(str) is not.


buildObject() is not working in latest version of xmlbuilder

xmlbuilder has been updated to v8.0.0 last week. The buildObject() in the xml2js.Builder object is not compatible with this version of xmlbuilder.

I've tried it with 7.0.0 and tests passed. Can't try it with 8.x, since it drops compatibility with older nodejs.

Is it possible to fix the version in the package.json because it always fetches the latest version of xmlbuilder which is v8.0.0?

The version is fixed: ^4.1.0 which is supposed to only install versions 4.1.x… (on my system it somehow installs 4.2.1 but that works as well).

Thanks for the reply. I guess I have misunderstood the caret, but got it cleared now
It is installing 4.2.1 only...


Design guidance for pattern pages

Currently we have not fully designed or thought about how the guidance for patterns will be laid out.

Need to
Look at what other design system do
How to we want to inform the users including: examples, code, guidance and accessibility.


provide example demonstrating CONAN_INCLUDE_DIRS_XXX

I'm sorta noticing that the CONAN_INCLUDE_DIRS_XXX isn't substantiated by the CMakeDeps CMakeToolchain generators,
❯ ls
BZip2-Target-release.cmake            ZLIB-release-armv8-data.cmake         conanbuild.sh                         libxcrypt-Target-release.cmake        pcre-Target-release.cmake
BZip2-release-armv8-data.cmake        ZLIBConfig.cmake                      conanbuildenv-release-armv8.sh        libxcrypt-config-version.cmake        pcre-config-version.cmake
BZip2Config.cmake                     ZLIBConfigVersion.cmake               conanrun.sh                           libxcrypt-config.cmake                pcre-config.cmake
BZip2ConfigVersion.cmake              ZLIBTargets.cmake                     conanrunenv-release-armv8.sh          libxcrypt-release-armv8-data.cmake    pcre-release-armv8-data.cmake
BZip2Targets.cmake                    argon2-Target-release.cmake           deactivate_conanbuild.sh              libxcryptTargets.cmake                pcreTargets.cmake
CMakeCache.txt                        argon2-config-version.cmake           deactivate_conanrun.sh                module-BZip2-Target-release.cmake     utf8cpp-Target-release.cmake
CMakeFiles                            argon2-config.cmake                   http_parser-Target-release.cmake      module-BZip2-release-armv8-data.cmake utf8cpp-config-version.cmake
CMakePresets.json                     argon2-release-armv8-data.cmake       http_parser-config-version.cmake      module-BZip2Targets.cmake             utf8cpp-config.cmake
FindBZip2.cmake                       argon2Targets.cmake                   http_parser-config.cmake              module-ZLIB-Target-release.cmake      utf8cpp-release-armv8-data.cmake
FindZLIB.cmake                        cmakedeps_macros.cmake                http_parser-release-armv8-data.cmake  module-ZLIB-release-armv8-data.cmake  utf8cppTargets.cmake
ZLIB-Target-release.cmake             conan_toolchain.cmake                 http_parserTargets.cmake              module-ZLIBTargets.cmake
❯ grep -r CONAN_INCLUDE_DIRS
~/inspircd/build master* ⇣⇡                                                                                12:33:47 PM
❯

I had to go rooting around to find the INCLUDE DIR path names look like
include_directories(
  include/
  ${libxcrypt_INCLUDE_DIRS_RELEASE}
)

But, it don't work. Is it broke? Why'd they even change this it looks like Conan 1.x did what it was supposed to do?

Oh hey I think I figured this out now, I was on the right path, you just have to make sure to require it for those variables to work:
find_package(libxcrypt REQUIRED)

include_directories(
  include/
  ${argon2_INCLUDE_DIR}
)

But the thing is, just finding that variable was like ... to be honest I don't even know if thats the way you're supposed to do it because that seems counter intuitive? I don't know, I just haven't had much luck finding the right answers maybe..

Hi @paigeadelethompson
Thanks for your suggestion.
The thing is that such variables are internal implementation detail of the CMakeDeps generator. They shouldn't be used directly, also because modern CMake good practices discourage that approach.
The recommended approach is to link with the target, and such target will bring everything in it: the include-dirs, the lib-dirs, the libs, the necessary flags and definitions, etc. So mostly:

find_package(mydep REQUIRED)

target_link_libraries(mylib_or_app mydep::mydep)

The name of the target is by default the name of the package::package, but it can vary for open source third parties with different conventions. They will typically be printed on screen when find_package() finds the package.

yeah I couldn't quite figure out how to get XCode / CMake / Conan working together right either. XCode builds my project ok, but it's not picking up any of my Conan dependencies for some reason. I actually switched to using target_include_directories for some things, I've been working in a different branch:
https://github.com/paigeadelethompson/clandestine/blob/services/ircd/src/CMakeLists.txt#L44
I wonder though I'm still using include_directories in places where I have lots of targets like here: https://github.com/paigeadelethompson/clandestine/blob/services/ircd/src/modules/CMakeLists.txt#L3
But I wonder now if maybe if include_directories is breaking Conan and causing things like target_link_libraries to not work correctly:
https://github.com/paigeadelethompson/clandestine/blob/services/ircd/src/modules/extra/CMakeLists.txt#L553
In XCode what I'm noticing is that when I try to build, if(sqlite3_FOUND) will evaluate to true but target_link_libraries(m_sqlite3 clandestine SQLite::SQLite3) never links because when it XCode tries to link there are unresolved symbol errors. However building with CMake from command line this works fine. So I'll check when I get a chance later today, I imagine there's probably something somewhere that I've overlooked, but at least its coming along some :)


chore: replace anymap with anymap2

I hereby agree to the terms of the GreptimeDB CLA.
Refer to a related PR or issue link (optional)
What's changed and what's your intention?
This PR replaces the anymap dependency in plugin crate with anymap2 in that the recent toolchain gives a warning:
>    --> /home/lei/.cargo/registry/src/index.crates.io-6f17d22bba15001f/anymap-1.0.0-beta.2/src/any.rs:37:40
>     |
> 37  |                 unsafe { Box::from_raw(raw as *mut $t) }
>     |                                        ^^^^^^^^^^^^^^
> ...
> 144 | impl_clone!(dyn CloneAny + Send);
>     | -------------------------------- in this macro invocation
>     |
>     = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
>     = note: for more information, see issue #127323 <https://github.com/rust-lang/rust/issues/127323>
>     = note: this warning originates in the macro `impl_clone` (in Nightly builds, run with -Z macro-backtrace for more info)

Related issues:

https://github.com/chris-morgan/anymap/issues/53
https://github.com/rust-lang/rust/issues/127323

Looks like anymap is no longer under maintainence, we should switch to anymap2.
Checklist

[ ] I have written the necessary rustdoc comments.
[ ] I have added the necessary unit tests and integration tests.
[ ] This PR requires documentation updates.

@zyy17 @shuiyisong Please let me know if there's any downstream projects that may be affected by this change and I will fix them as soon as this get's merged.

It's strange that anymap2 doesn't seem to be under maintenance either.

It's strange that anymap2 doesn't seem to be under maintenance either.

I don't think simple crates like anymap needs continuous updates, simply because there's no compiler warning in anymap2.

It's strange that anymap2 doesn't seem to be under maintenance either.

I don't think simple crates like anymap needs continuous updates, simply because there's no compiler warning in anymap2.

Or we can maintain the anymap in our own utils codebase.


Re-implement node searching

Does this PR close any open issues?
Closes #363
Give a longer description of what this PR addresses and why it's needed
I re-implemented node searching, using similar UI and functions to those that exist in multilink. This new search bar acts as if you're clicking. That is, if the node is unselected it will be selected, and if it's selected it will be unselected. This might not be ideal, but to change it would require a rewrite of quite a bit of code. Let me know how the UX is. The search also works within aggregated nodes.
I didn't test with any intermediary nodes, so that might be broken.
I also adjusted some margins that weren't needed after this change
Provide pictures/videos of the behavior before and after these changes (optional)
New search bar:

Are there any additional TODOs before this PR is ready to go?
TODOs:

[x] Test with intermediary nodes table

Works with the intermediary nodes. One behavior that's unexpected though is that if you search for another node then both rows will be selected -- I'm not sure if that's the behavior you are envisioning.
Both rows end up being selected.

Yeah, I thought it might be a bit weird. I'll make an issue


Missing E999

E999 indicates failure to generate AST (e.g. SyntaxError).

Why this one is not included?

Because it is awaiting your PR, @lipis! 😄


Update CHANGEME.md

A new verse is added.

Seems to be a duplicate of #1063

I tried it several times just to add a reviewer but it dint happened in my case that's why.


Update src with latest vendor.sh stuff

I think someone forgot to run vendor.sh after it was updated so
this just syncs things up.
Signed-off-by: Doug Davis<EMAIL_ADDRESS>

LGTM 🐰

LGTM