Use MQTT for Shelly Thermostatic Radiator Valves

Hi folks,

Continuing the discussion from New smart wifi radiator valves from Shelly

Thought it would never happen again, but finally I have ordered a Shelly TRV to experiment. But not quite sure what is the best way to control it.

For my other Shelly devices (mostly plug-S) I use MQTT instead of http communication. Because it seems a bit of waste to keep polling, while the Shellies can simply send a message via MQTT for each status change.

Since the Shelly TRV's run on battery, I would like to mimimize the traffic as much as possible. So I "think" mqtt again would be adviced more than http requests. However no messages arrive from my TRV in the input topic. And the MQTT broker is configured correctly in the Shelly web interface, because I can open and close the valve via MQTT commands...

Does anybody has tips for me that I can try??

@mudwalker: do you have meanwhile become more experienced in using these valves via MQTT? It was very kind of you to share your flow at the time being. In your old flow, you were using http requests to control your valve. Is that still the case, or did you switch to MQTT commands meanwhile perhaps?


I know I'm going to regret asking.... but I assume that you've read & tried the topics shown in the api guide - API Reference ?

Shelly TRV: MQTT

When configured for MQTT, Shelly TRV sends values from its internal sensors on the following topics:

  • shellies/shellytrv-<id>/info: publishes a JSON payload with the content of HTTP /status endpoint

Not sure why you should regret...

Yes you are absolutely right. That topic is available, as you can see with MQTT Explorer:


And indeed the messages on this topic contain the information that I need:

 "thermostats": [
      "pos": -1,
      "target_t": {
        "enabled": true,
        "value": 31,
        "value_op": 8,
        "units": "C"
      "tmp": {
        "value": 18,
        "value": 17.8,
        "units": "C",
        "is_valid": true
      "schedule": true,
      "schedule_profile": 1,
      "boost_minutes": 0,
      "window_open": false

But what I don't really get is when the TRV will send such messages. Since the TRV wants to be as much low power as possible, it will only send such messages when "something" has changed?

But when I use MQTT explorer, you see in the message history ot this topic that the timestamps of those messages are very random:

17-12-2022 23:54:00 
17-12-2022 23:19:01(-34.98 minutes) 
17-12-2022 23:00:11(-18.83 minutes) 
17-12-2022 22:54:00(-6.19 minutes) 
17-12-2022 21:54:00(-60 minutes) 
17-12-2022 21:17:01(-36.98 minutes) 
17-12-2022 20:53:59(-23.04 minutes) 
17-12-2022 19:15:01(-98.97 minutes) 
17-12-2022 16:53:59(-2.35 hours) 
17-12-2022 10:06:01(-6.8 hours) 
17-12-2022 08:04:03(-2.03 hours) 
17-12-2022 07:54:01(-10.03 minutes) 
16-12-2022 23:56:02(-7.97 hours) 
16-12-2022 23:54:00(-2.03 minutes) 
16-12-2022 23:32:30(-21.51 minutes) 

So this is not periodically. And certainly not often. But it is also not when the temperature changes, because then I would have received a LOT more messages. And it is also not when we e.g. have manually pressed the TRV buttons, because it is still untouched on my table (i.e. not operational yet).

Summarized: I don't know what is the trigger in the TRV to send an MQTT message. Don't know either if I can/should change this trigger. Or perhaps it is better if I just call the http API at moments when I need the data. :exploding_head:

It could very well be that this is one of the values that triggers it, but usually per 0.5 degrees or something. I did not check the documentation, but there could be an "installed" or calibated flag (my zwave onces have that) - ie. if it is on your table, it is not installed, it might not report as expected.

Not sure at the moment what is the best way to use this TRV in combination with Node-RED.

I first thought that Node-RED had to control everything: having schedules in Node-RED, that keep track of the room temperatures, do pid control and continiously adjust the temperature of the TRV. But that seems quite some logic to implement, and quite some communication with the TRV. Which will not be good for the battery life...

But the TRV also allows you to set schedules on it, where you can specify desired temperatures for specific times on specifc days:

So perhaps it is better if I just manage schedules in my Node-RED, and I upload these via MQTT or http to my TRV. And from there on I leave it to the TRV, so he has to manage that the temperature is ok according to the uploaded schedules. Then I have a simple flow, and a minimum of communication between Node-RED and the TRV. And it will even work if my Node-RED should be down for some reason. Does anybody see some disadvantages in such a setup?

I assume I can upload a schedule something like this:

Although some things are not quite clear to me about such a setup:

  1. When you upload a schedule to the TRV, the TRV will try to manage to follow it. And you can easily go to manual mode by pressing the buttons on the TRV, to change the temperature immediately. But I don't see how you can go back to automatic mode (i.e. to the schedule) via the buttons on the TRV.

  2. Depending on the outside temperature, it can talk longer or not to reach that desired temperature on the specified time. Not sure how the TRV can manage to accomplish that. Perhaps it is doing it somehow via this setting:

That is indeed possible. Will need to install it as soon as possible then...

I found the answer in this interesting article:
If a set point is manually entered when a schedule is running, the new set point will override the schedule until the next time a temperature change is defined in the schedule.

So if you change the setpoint temperature manually via the buttons, that afterwards you also manually need to change the setpoint again (only if you want to go back to the original scheduled temperature). The display on the TRV shows the current temperature and the set point as it is being adjusted.

Read some other interesting things in that same article:

  • TRV will perform its automatic calibration so it understands the fully open and close limits of the radiator valve.
  • A schedule can consist of up to five unique profiles and each profile can consist of up to 20 temperature changes at different times during the day.

That means it times how long it takes to drive from open to closed (and probably back again).

1 Like

There was an occasion recently where an unattached TRV went into a 'continuous calibration' mode (in/out/in/out repeat) after the battery went flat. Once installed on the Radiator, it was able to calibrate correctly and sorted itself out.

I drive my TRV using MQTT and request status every 37 seconds, but this does need to be reviewed, no need for that frequency with such a slow system attached. One of the messages that comes back is the battery charge level, I monitor this and send a Telegram message when it gets to 30%. Commands are only sent when the value changes (Filter node).

With restarts when the flow is modified (such as after installation of OTGW) it would seem that the battery life is a solid 3 months, once everything settles down I am sure this can be extended by quite some time. The other precaution taken i that if the heating is not required all comms are blocked except a 12 hour Status request to check batter level.

There is currently a problem with the PID control as it seems to close the valve after every command, but to be honest, I think that a change to the persistence value in the PID node will sort this out. Consequently, at the moment, the valve is just used as Open/Shut, which to be honest, works well enough.

Unfortunately, I have been rather busy recently with Family stuff, so not been able to check it out.


Thanks for sharing your experiences!!

So you measure the frequency often, to control the temperature yourself.

Do you have any idea about:

  1. Would it be a decent setup to leave control to the trv itself, by uploading a schedule via Node-RED. And so let the TRV do the necessary to follow that schedule?
  2. Why my 'info' messages (see my second post above) arrive automatically at such weird timings? I have no idea at which conditions the trv decides to send an info message...

Which PID node are you using? If it is node-red-contrib-pid then I should be able to help with this. In fact I would be fascinated to see how it works with that valve as I am thinking of trying one myself.

1 Like

@BartButenaers You can leave the TRV to control itself, but I do like to be able to tweak things. We are quite frugal with our heating (as are we all!), e.g. during the afternoon, we have the temperature set so that we aren't cold, but, it might be considered cool to visitors. I can then set a Manual Temperature which is suitable for them. You could do this by sending a one off, but for me, being able to control the temperature through Node-RED gives me a visual status of what is going on. I had a lot of help recently generating a basic flow for setting a schedule. This could be modified to add days of the week if needed.

From memory, the status is sent on the TRV's schedule, which was why I started to request the status for my own convenience.

@Colin The problem is probably mine, and yes, I am using your Node. What happens is that as a new PID value is sent, the TRV closes and then opens to the correct percentage, which seems a waste of battery to me, and provides some 'noise pollution' which being an Engineer, I hear every time it operates and to be honest, grates on my nerves!! I have not isolated the cause of the problem yet, but as I can see it on the graph of the output of the PID Node. This suggests that it might be from there. Basically, the Valve is being commanded to Close and Open at very change. I need longer to tie it down.

I will need to get back into this in the New Year, but Grandchildren's Birthdays, Christmas and Family visits will get in the way until then!

Our first cold snap, the new boiler misbehaving so that we had minimal heat (boiler @ 38deg!) and a week away have not helped!

1 Like

Add a debug showing what is going into the PID node and check that all the messages have good PV values. Check that you are not accidentally sending in something with one of the topic values that mean things to the node.

1 Like

Provided the clock on the TRV is set correctly I would have thought that sending a schedule would be the way to go. I thought the whole point of an automated TRV is that it has its own controls. There are still loads of things that can be controlled from Node-red, modes, away days etc

A good point raised in another thread is that it is worth setting up a monitor of TRV temperature against room temperature to track any variations between the schedule and real life, just to reassure yourself that they are working OK.

Most battery operated devices seem to have a mind of their own on when they report back, but obviously the fewer reports there are the longer the battery lasts

That is quite short in comparison to the 2 years that the mention all over the web...
I'm very curious if it will be better if I upload the schedule via Node-RED, and then let it live its own life as much as possible...

@Colin I will re-activate the Debug Nodes, however, the graph has been showing valid OP and SP values with PV showing the current temperature of the room, that is until I re-arranged the flows taking functions away from my Opto22 Controller and passing them to Node-RED. I just need to sit and sort those out. When it was controlling, other than tweaking the Values, it did appear to be controlling correctly, even if it was 'slightly' underdamped with it's wildly swinging values!! Time is what is needed, however, my current thinking is that for now ON/OFF control is fine with the inertia of the system. In the interests of this application, I can pursue the PID route further, but it would mean more power consumption.

@BartButenaers Running the Shelley as a stand-alone has to be the way to preserve Battery Power. My current thoughts are to load the schedule once a day, with overrides sent as an when. TRV complete with Battery Status (I think) will come back as you load the new schedule, but loading this once a day means that the TRV does not need to keep reconnecting to Wi-Fi, which has to go a long way to save the battery, gathering ststus at the same time would not be too great an overhead for the battery once connected.

Of course, as with all sales literature, what is advertised and 'real world' figures are like Chalk and Cheese, but then we, as the consumer, have come to expect that! :rofl:

That is indeed a good approach I think. At least if the TRV does a good job on its own...
But then our Node-RED is still in control, with minimum of communication.

I had a look at your flow last night, but I didn't find any ways to set the schedule via Node-RED and MQTT to the TRV. But perhaps I have overlooked it. And I didn't find it in the Shelly API docs or on the web either. So if you have any simple examples, I would appreciate a lot if you could share it.

Sorry to disturb you this much, because I realize you are very busy at the moment. But the wife at the moment has the impression that the Shelly TRV is just one of those many devices I bought, which will never see the daylight...

When you said

I thought you meant that the output of the PID node went to 0 and immediately back to a good value again without a change in input temperature. That is why I suggested checking what is going into the PID node to make sure there are no spurious temperature values or auto/manual switch or similar going into the node.

@BartButenaers I currently read Context Memory for the current setpoint and then feed this in through Change Node 'set msg.setpoint'. I can look at sending a schedule to the TRV over the next 'few' days, it is not something I have investigated yet, just 'thinking out loud'.

@Colin Let me set things back up so that the new flow sends and reads the new data locations correctly and I can start looking at the operation again.

It is not a problem asking questions, I can have a think, the problem is being able to get the time to play in the lead up to Christmas. My programming skills are rudimentary and it can take me a while to complete what others may consider a simple task. I am in awe at the number of pieces of code that members of the Forum just rattle off to help someone with their problems, I read these and get little pointers as to what might help my application!

So, the ball is in my court for both these things and going the alternative route for the schedule means that running the PID would defeat the object of 'minimum' communication with the Shelly. But as Colin is interested in seeing the PID run in this particular application, I would like to try to oblige. I do have a second TRV, but it is just a bit too wide to fit the current radiator inlets!

1 Like

Oh thinking out loud is appreciated a lot. I will try to think out loud also :wink:

I must admit that I am kind of surprised that it is so hard to find simple examples. Perhaps it is somewhere available and easy to find, but then I have overlooked it...

Via some facebook folks I finally found this link from Shelly support. Note that you need to create an account first and press numerous confirmation buttons.

On that link you will find a nice overview of multiple http commands for the TRV. I will share a copy of the content here, for easy access. BUT ALL CREDITS GO TO Devil, THE AUTHOR OF THE ARTICLE IN THE ABOVE LINK !!!!*

  • Auto Temp Control:

    ON = 1 , OFF= 0

  • Auto Temp Control ON and set Target-Temp:

    Target-Temp. 4-31 degree

  • Auto Temp Control OFF and set Valve-Position:

    Valve-Position in percent 0-100 (%)

  • Switch Schedule ON/OFF:

    ON = 1 , OFF= 0

  • Switch Schedule ON/OFF and set Schedule Profil 1-5:

    ON = 1 , OFF= 0
    Profil = 1-5

  • Boost Start in Min:
  • Switch Accelerated heating (reduce time to reach the target temperature):

    ON = 1 , OFF= 0

  • Set minimum position of valve in percent:

    Valve-Position in percent 0-10 (%)

  • Set Display brightness :

    1=Low, 4=Normal, 7=High

  • Display Rotate screen (180°):

    ON = 1 , OFF= 0

  • Child Lock:

    ON = 1 , OFF= 0

  • Calibration:
  • Change timer profiles:


    schedule_profile: the profile number 1 (linvingroom)

    schedule_rules: each entry must be separated by a comma

    • Each block can be seen here separately separated by the hyphen/minus (-) (0830-0123456-20.5)

    • First block (0830): Time hour and minute written together, note leading zero in example 08:30

    • Second block (0123456):

      • 0 = Monday
      • 1 = Tuesday
      • 2 = Wednesday
      • 3 = Thursday
      • 4 = Friday
      • 5 = Saturday
      • 6 = Sunday

      In the example they specified from Monday to Sunday

    • Third and last block (18.5): The desired temperature in the example 18.5°C

Thanks to this article from Devil, at least I know now what the information in all the blocks of the schedule command mean :+1: