Tado API Guide - updated for 2019


Tado is a brilliant smart thermostat. But their API is very poorly documented. This is an updated guide for 2019. I am indebted to Stephen C Phillips' original documentation.

Getting started

You will need:

  • A Tado (duh!)
  • Your Username (usually your email address)
  • Your Password
  • A Client Secret

Getting the client secret

I'm using this client secret:
wZaRN7rpjn3FoNyF5IFuxg9uMzYJcvOoQ8QWiIqS3hfk6gLhVlG57j5YNoZL2Rtc
This secret may change in the future. In the examples, I'll shorten it to wZa to make it easier to read. You will need to use the full length secret when running this code.

To get the current secret, you can visit https://my.tado.com/webapp/env.js and get the secret from there.

var TD = {
    config: {
        version: 'v587',
        tgaRestApiEndpoint: 'https://my.tado.com/api/v1',
        tgaRestApiV2Endpoint: 'https://my.tado.com/api/v2',
        susiApiEndpoint: 'https://susi.tado.com/api',
        oauth: {
            clientApiEndpoint: 'https://my.tado.com/oauth/clients',
            apiEndpoint: 'https://auth.tado.com/oauth',
            clientId: 'tado-web-app',
            clientSecret: 'wZaRN7rpjn3FoNyF5IFuxg9uMzYJcvOoQ8QWiIqS3hfk6gLhVlG57j5YNoZL2Rtc'
        }
    }
};

If that ever changes, you will need to open your web browser's development tools, and then look in the network tab. Then, log in to https://my.tado.com/webapp/.

You should see the token:
Debug screen of a web browser.

Get Bearer Token

These examples use the curl command on Linux.

Here's how to turn your username and password into a "Bearer Token" - this is needed for every subsequent API call:

curl -s "https://auth.tado.com/oauth/token" -d client_id=tado-web-app -d grant_type=password -d scope=home.user -d username="you@example.com" -d password="Password123" -d client_secret=wZa

The response will be:

{
    "access_token": "abc",
    "token_type": "bearer",
    "refresh_token": "def",
    "expires_in": 599,
    "scope": "home.user",
    "jti": "xyz-123"
}

The real access_token will be very long. I've shortened it to abc make things easier to read in these examples.

The access token expires after 600 seconds. You can either request a new one with the username and password, or use the provided refresh_token like so:

curl -s "https://auth.tado.com/oauth/token" -d grant_type=refresh_token -d refresh_token=def -d client_id=tado-web-app -d scope=home.user -d client_secret=wZa

Get your details

The next step is to get your homeId - this will also be needed for subsequent API calls:

curl -s "https://my.tado.com/api/v1/me" -H "Authorization: Bearer abc"

You'll get back your data, like this:

{
    "name": "Terence Eden",
    "email": "you@example.com",
    "username": "your_user_name",
    "enabled": true,
    "id": "987654321",
    "homeId": 123456,
    "locale": "en_GB",
    "type": "WEB_USER"
}

Your homeId is what's important here. I'm going to use the example 123456 - you should use your own.

Check it all works

This request will check that you've got the right details.

curl -s "https://my.tado.com/api/v2/homes/123456" -H "Authorization: Bearer abc"

You'll get back information about your installation. I've redacted mine for privacy.

{
    "id": 123456,
    "name": " ",
    "dateTimeZone": "Europe/London",
    "dateCreated": "2015-12-18T19:21:59.315Z",
    "temperatureUnit": "CELSIUS",
    "installationCompleted": true,
    "partner": " ",
    "simpleSmartScheduleEnabled": true,
    "awayRadiusInMeters": 123.45,
    "usePreSkillsApps": true,
    "skills": [],
    "christmasModeEnabled": true,
    "contactDetails": {
        "name": "Terence Eden",
        "email": " ",
        "phone": " "
    },
    "address": {
        "addressLine1": " ",
        "addressLine2": null,
        "zipCode": " ",
        "city": " ",
        "state": null,
        "country": "GBR"
    },
    "geolocation": {
        "latitude": 12.3456789,
        "longitude": -1.23456
    },
    "consentGrantSkippable": true
}

Get your data

OK, here's where the fun begins. This gets the data about your installation - including firmware details, device names, etc.

curl -s "https://my.tado.com/api/v2/homes/123456/zones" -H "Authorization: Bearer abc"

Here's what you get back - I've redacted some of my details.

[{
    "id": 1,
    "name": "Heating",
    "type": "HEATING",
    "dateCreated": "2015-12-21T15:46:45.000Z",
    "deviceTypes": ["RU01"],
    "devices": [{
        "deviceType": "RU01",
        "serialNo": " ",
        "shortSerialNo": " ",
        "currentFwVersion": "54.8",
        "connectionState": {
            "value": true,
            "timestamp": "2019-02-13T19:30:52.733Z"
        },
        "characteristics": {
            "capabilities": ["INSIDE_TEMPERATURE_MEASUREMENT", "IDENTIFY", "OPEN_WINDOW_DETECTION"]
        },
        "batteryState": "NORMAL",
        "duties": ["ZONE_UI", "ZONE_LEADER"]
    }],
    "reportAvailable": false,
    "supportsDazzle": true,
    "dazzleEnabled": true,
    "dazzleMode": {
        "supported": true,
        "enabled": true
    },
    "openWindowDetection": {
        "supported": true,
        "enabled": true,
        "timeoutInSeconds": 1800
    }
}, {
    "id": 0,
    "name": "Hot Water",
    "type": "HOT_WATER",
    "dateCreated": "2016-10-03T11:31:42.272Z",
    "deviceTypes": ["BU01", "RU01"],
    "devices": [{
        "deviceType": "BU01",
        "serialNo": " ",
        "shortSerialNo": " ",
        "currentFwVersion": "49.4",
        "connectionState": {
            "value": true,
            "timestamp": "2019-02-13T19:36:17.361Z"
        },
        "characteristics": {
            "capabilities": []
        },
        "isDriverConfigured": true,
        "duties": ["ZONE_DRIVER"]
    }, {
        "deviceType": "RU01",
        "serialNo": " ",
        "shortSerialNo": " ",
        "currentFwVersion": "54.8",
        "connectionState": {
            "value": true,
            "timestamp": "2019-02-13T19:30:52.733Z"
        },
        "characteristics": {
            "capabilities": ["INSIDE_TEMPERATURE_MEASUREMENT", "IDENTIFY", "OPEN_WINDOW_DETECTION"]
        },
        "batteryState": "NORMAL",
        "duties": ["ZONE_UI", "ZONE_LEADER"]
    }],
    "reportAvailable": false,
    "supportsDazzle": false,
    "dazzleEnabled": false,
    "dazzleMode": {
        "supported": false
    },
    "openWindowDetection": {
        "supported": false
    }
}]

State

This command will tell you if you're home or not. Or, in other words, whether the Tado thinks you're nearby:

curl -s https://my.tado.com/api/v2/homes/123465/state -H "Authorization: Bearer abc"

This is what you'll get back if you're at home

{"presence":"HOME"}

Zones

My Tado has two "Zones". 0 is for Hot Water, 1 is for Heating. Yours may be different.

Hot Water Information

curl -s https://my.tado.com/api/v2/homes/123456/zones/0/state -H "Authorization: Bearer abc"

Here's information about your hot water:

{
    "tadoMode": "HOME",
    "geolocationOverride": false,
    "geolocationOverrideDisableTime": null,
    "preparation": null,
    "setting": {
        "type": "HOT_WATER",
        "power": "OFF",
        "temperature": null
    },
    "overlayType": null,
    "overlay": null,
    "openWindow": null,
    "nextScheduleChange": {
        "start": "2019-02-13T19:00:00Z",
        "setting": {
            "type": "HOT_WATER",
            "power": "ON",
            "temperature": null
        }
    },
    "link": {
        "state": "ONLINE"
    },
    "activityDataPoints": {},
    "sensorDataPoints": {}
}

Heating

It's much the same for Heating information:

curl -s https://my.tado.com/api/v2/homes/123456/zones/1/state -H "Authorization: Bearer abc"

This also gets you humidity data etc:

{
    "tadoMode": "HOME",
    "geolocationOverride": false,
    "geolocationOverrideDisableTime": null,
    "preparation": null,
    "setting": {
        "type": "HEATING",
        "power": "ON",
        "temperature": {
            "celsius": 15.00,
            "fahrenheit": 59.00
        }
    },
    "overlayType": null,
    "overlay": null,
    "openWindow": null,
    "nextScheduleChange": {
        "start": "2019-02-13T17:30:00Z",
        "setting": {
            "type": "HEATING",
            "power": "ON",
            "temperature": {
                "celsius": 18.00,
                "fahrenheit": 64.40
            }
        }
    },
    "link": {
        "state": "ONLINE"
    },
    "activityDataPoints": {
        "heatingPower": {
            "type": "PERCENTAGE",
            "percentage": 0.00,
            "timestamp": "2019-02-13T10:19:37.135Z"
        }
    },
    "sensorDataPoints": {
        "insideTemperature": {
            "celsius": 16.59,
            "fahrenheit": 61.86,
            "timestamp": "2019-02-13T10:30:52.733Z",
            "type": "TEMPERATURE",
            "precision": {
                "celsius": 0.1,
                "fahrenheit": 0.1
            }
        },
        "humidity": {
            "type": "PERCENTAGE",
            "percentage": 57.20,
            "timestamp": "2019-02-13T10:30:52.733Z"
        }
    }
}

Weather

Tado also provides you with data about the external weather:

curl -s https://my.tado.com/api/v2/homes/123456/weather -H 'Authorization: Bearer abc'

You get back a basic weather report for your location:

{
    "solarIntensity": {
        "type": "PERCENTAGE",
        "percentage": 68.10,
        "timestamp": "2019-02-10T10:35:00.989Z"
    },
    "outsideTemperature": {
        "celsius": 8.00,
        "fahrenheit": 46.40,
        "timestamp": "2019-02-10T10:35:00.989Z",
        "type": "TEMPERATURE",
        "precision": {
            "celsius": 0.01,
            "fahrenheit": 0.01
        }
    },
    "weatherState": {
        "type": "WEATHER_STATE",
        "value": "CLOUDY_PARTLY",
        "timestamp": "2019-02-10T10:35:00.989Z"
    }
}

Controlling your home

It's possible to turn the heating and hot water on / off.

Turn Heating On

This is a PUT request

curl -s 'https://my.tado.com/api/v2/homes/123456/zones/1/overlay' -X PUT -H 'Authorization: Bearer abc' -H 'Content-Type: application/json;charset=utf-8' --data '{"setting":{"type":"HEATING","power":"ON","temperature":{"celsius":21,"fahrenheit":69.8}},"termination":{"type":"MANUAL"}}'

Just to make it easier to read, this is the JSON data that you have to PUT:

{
    "setting": {
        "type": "HEATING",
        "power": "ON",
        "temperature": {
            "celsius": 21,
            "fahrenheit": 69.8
        }
    },
    "termination": {
        "type": "MANUAL"
    }
}

If it has worked, you'll get back this response:

{
    "type": "MANUAL",
    "setting": {
        "type": "HEATING",
        "power": "ON",
        "temperature": {
            "celsius": 21.00,
            "fahrenheit": 69.80
        }
    },
    "termination": {
        "type": "MANUAL",
        "projectedExpiry": null
    }
}

End Manual Heading Mode

This is a simple DELETE command:

curl -s 'https://my.tado.com/api/v2/homes/123456/zones/1/overlay' -X DELETE -H 'Authorization: Bearer abc'

Turn on Hot Water

Much the same as before

curl -s 'https://my.tado.com/api/v2/homes/123456/zones/0/overlay' -X PUT -H 'Content-Type: application/json;charset=utf-8' -H 'Authorization: Bearer abc'--data '{"setting":{"type":"HOT_WATER","power":"ON"},"termination":{"type":"MANUAL"}}'

Turn off Hot Water

Again, a DELETE

curl -s 'https://my.tado.com/api/v2/homes/123456/zones/0/overlay' -X DELETE -H 'Authorization: Bearer abc' 

Historic Information

You can get a complete view of historic data with:

curl -s 'https://my.tado.com/api/v2/homes/123456/zones/1/dayReport?date=2018-02-14' -H 'Authorization: Bearer abc' 

The date at the end is in ISO8601 format. You'll receive info on internal and external temperature, humidity levels, whether the heating and hot water were on, and a few other bits and bobs.

What's Next?

There are a bunch of other things you can do with the API, like setting a schedule etc. Sadly, I don't have time to document them all. But this should be enough to get you detailed information, and basic control.

I'd love it if someone could make OpenAPI documentation for this.


Share this post on…

60 thoughts on “Tado API Guide - updated for 2019”

    1. says:

      No. Because every request needs to pass an Authorization header. You could build your own proxy service.

      Reply
        1. Richard Swain says:

          Just a warning - You don't want to be passing usernames & passwords in the url. Unlike body content the query string params aren't encrypted.

          Reply
          1. Martijn van der Woud says:

            Actually the query string params are encrypted with SSL. However they may very well show up in web server logs

            Reply
  1. Omar says:

    Hi, thanks for the info. What other termination types are supported? you listed the manual one but I’m looking for the dynamic one that terminates at the next scheduled time block
    “termination”:{“type”:”MANUAL”}

    Reply
  2. W says:

    Can anyone tell me if the ambient light sensor in the radiator valve is exposed in any of Tado's endpoints?

    Reply
  3. AndrewFG says:

    Dear Terence,

    Many thanks for sharing this information. You asked if anyone has an OpenAPI specification for Tado, and I think that there is indeed one written by Dennis Frommknecht on the OpenHAB github on the link below.

    https://github.com/openhab/openhab2-addons/blob/master/bundles/org.openhab.binding.tado/src/main/api/tado-api.yaml

    I think his specification is not fully complete, and would benefit from being completed with your own knowledge added. For example, I want to add “device:batteryState” to this specification. Any thoughts?

    Reply
      1. AndrewFG says:

        😉

        I guess I was hoping that you might add some of your own knowledge too 🙂

        Reply
  4. Tim says:

    I guess they changed it again?! 😦

    It looks like hotwater zones don’t have an overlay and the DELETE command no longer works to turn hot water off.

    Reply
    1. Tim D says:

      Looks like to turn things off is much the same as the turn on (PUT request) except with power set to OFF etc.

      Cheers.

      Reply
  5. Michael Senger says:

    Hello,
    can someone tell me, what “usePreSkillsApps” is and what kind of data it will be show?

    Reply
    1. says:

      It's a boolean field. So it will only show true or false. But I don't know what it represents. I suggest asking Tado directly.

      Reply
    2. Joris says:

      Tado changed their system to a subscription service that offers extra features. They are called “skills”.
      For instance in the old version (the one I have) having your heating turned on/off based on whether you are home is a free feature. In the current/new version if you buy a Tado system you have to pay a subscription to use this service.

      https://support.tado.com/hc/en-gb/articles/360015213512-What-is-Auto-Assist-

      I presume that that flag is used to determine if you are on the old or the new system.

      Reply
  6. Georgi P says:

    If someone is interested here are the APIs to witch Home/Away mode and Open Window.
    It will work if you are not using the “auto-assist” (subscription) from Tado. In order to activate away mode you need to have geofencing active and away from home. For open window to work first an open window must be detected by Tado.

    Home/Away:
    PUT – https://my.tado.com/api/v2/homes//presence
    {
    “homePresence”: “AWAY”
    }

    Open Window:
    POST – https://my.tado.com/api/v2/homes//zones//state/openWindow/activate

    Reply
  7. Jacopo Scarpellini says:

    Is there a way to change the temperature offset using the API?
    This could be useful to solve the problems with the Smart TRV (the offset required depend on various factors and could be measured by an external sensors)

    Reply
  8. Jacopo Scarpellini says:

    when I type the following in Putty connected to my hassio

    core-ssh:~# curl -s "https://auth.tado.com/o scope=home.user -d username="myname@gmail.com" -d password="12345" -d client_secret=wZaRN7rpjn3FoNyF5IFuxg9uMzYJcvOoQ8QWiIqS3hfk6gLhVlG57j5YNoZL2Rtc

    I get:

    {"error":"invalid_grant","error_description":"Bad credentials"}core-ssh:~#

    I've tried with and without " around username and password, no sure if they are needed; it doesn't work anyway

    Any idea?

    Reply
    1. says:

      I've just tried, and it appears to work for me. Do you have an special characters in your password?

      Reply
        1. Jot Zet says:

          Hey,
          you have to encode you "+" / "plus sign", and use ...?username="name%2Btado@mail.com" for "name+tado@mail.com"
          This worked for me,
          kR, J

          Reply
  9. Christian says:

    If you have multiple thermostats in a room, you have to select a “Measuring device” in the TADO App. i assume this is the device that you get measurements for under the ‘zones//state’ (?)

    Is there no way to get measurements from the other thermostats in the room? Except by putting all thermostats in their own room?

    Reply
  10. John says:

    There is a new update, and no you can put Tado in Home/Away mode despite the geolocation of the users.
    Has someone found the api call to do this?

    Reply
  11. Jadranko says:

    Hi!

    Great info!

    How to get the ACTUAL (current) temperature inside the HWT (hot water tank)?

    I asko because at the very beginning of my tado installation the wall device/thermostat DID display this info too!! But, I had some other issues with the LED display so they changed the firmware. After that it all worked good BUT i lost the ability to see the actual water temperature in the tank??!!?!?? I mean WTF people?

    I did contact them several times but no progress...

    Once more thanks for your info.

    Best regards.

    Jadranko

    Reply
  12. Frédéric Mangeant says:

    Hi Terence

    MANY thanks for this explanation. Using a simple Ansible playbook I can now add my Tado in Grafana 🙂

    Frédéric

    Reply
  13. Stefano says:

    Hello,
    many thanks for sharing TADO's API functionalities!

    On the base on what I learned here, I was able to write a couple of Matlab scripts to replicate the TADO° graphics.
    In particular, I was interested in plotting temperature & humidity of all my rooms in a row, in order to find the best settings for the valve scheduling, and check if everything is working as expected:

    https://mega.nz/file/54tzVYaS#m5p3to73UGKtrlVXZL1t_ePx8l1Q5tUHXgivRbiNLnQ

    If someone using Matlab would like to give a try, I can share them.

    Stefano

    Reply
    1. Mathias Ditlevsen Bo says:

      Hi Stefano,
      I would like to try it out, if you’re still keen to share?

      Many thanks in advance ☺️

      Reply
      1. Stefano says:

        Hello Mathias,

        Sorry for my late answer, I was on holidays. I will pack the routines for you with some instructions as soon as possible.

        Have a nice day,
        Stefano

        Reply
  14. Stefano says:

    Hello Mathias,

    here is the link to the zipped routines:
    https://mega.nz/file/tl1AlapQ#sfk2Y8Bq9BAOtOiuhbp_q0AVE-uqVNstkl-Gmbrsnqs

    There are 4 routines:
    TADO.m creates a single room plot, inputs must typed into the code
    TADO_f.m is a Matlab function of TADO.m, inputs as passed as arguments
    TADO_multi.m calls TADO_f.m several times in order to have multiple plots (for different rooms), inputs must be typed into the code.
    TADO_multi_f.m the same as the latter, but the imputs are passed as arguments (is a function).

    They manage the heating only, but i guess it should be easy enough the extend them to the cooling too.

    In TADO_multi.m and TADO_multi_f.m, the variable "Day" equal to "0" (zero) means today, "1" means yesterday, "2" the day before yesterday, and so on.

    To make them work you have to get the Client Secrect, then your homeId is derived automatically, since this takes some time (the server response time), after you got the ID, you can write that number explicitally in the "homeId" variable. (See comments into the code).

    You have also to check the number of your zones (rooms), please note that Tado generates a new number each time you create a room (even if it was deleted just before) - regardless of its label. So, even if you have only 4 rooms the zones can have an odd numbering, for example: 1, 3, 4, 9 (depending on how much you have "played" with them).

    For convenience, I created two standalone applications: one for TADO_multi.m with Day = 0 (today) and one for TADO_multi.m with Day = 1 (yesterday) and named them as TADO_multi_0.exe and TADO_multi_1.exe, so that I can call them directly from my windows desktop.

    If you have any question, do not esitate to contact me.

    Reply
  15. Mathias Ditlevsen Bo says:

    Great!
    Thank you so much. Looking forward to play around with it ☺️

    Reply
  16. Thor says:

    Hi, thanks for a great guide on how to entering the Tado devices. Wrapping it into PHP. Good stuff, well done!

    In the current Tado app, there is an option to "Turn Off All Rooms", which bypasses any schedules set. Do you know what flag/option is set on the device to put it into this state?

    I am working on setting a working home or in the office schedule. What the code to skip if the tados are turned of due to e.g holiday.

    Again, thanks for the info so far 🙂

    Thor

    Reply
    1. @edent says:

      It is POSTing an overlay to `https://my.tado.com/api/v2/homes/123456/overlay`

      
      
      
      {
          "overlays": [
              {
                  "overlay": {
                      "setting": {
                          "power": "OFF",
                          "type": "HEATING"
                      },
                      "termination": {
                          "typeSkillBasedApp": "MANUAL"
                      }
                  },
                  "room": 2
              }
          ]
      }

      That's what I get when I look at the network requests on https://app.tado.com/en/main/home

      Reply
    1. @edent says:

      I don't know. I can't see anything about them. I suggest asking Tado directly.

      Reply
  17. Kevin says:

    Does anyone know what the batteryState value is other than "NORMAL"? What are the options to read

    "batteryState": "NORMAL",

    Reply
    1. @edent says:

      My Tado app alerts me when the batteries in it are low. I don't know what the API shows - so if I were you I'd just check if( $battery_state != "NORMAL" )

      Reply
  18. David Hills says:

    Huge thanks for your work and other contributors - notably @Equinoxefr whose Python work I have just started building on. Has anyone encountered any API call/download limits per hour? I am planning to grab 3+ years of full Day Report data from 7 zones and curious whether I should build in some lags? Aware of the need to refresh the access token if it runs that long.
    (A happy discovery from this work: On the IOS/web apps I can only see data back just over one year, but with API calls I can retrieve everything since I started with Tado >3 years ago.)

    Reply
    1. Matt says:

      David, I too am looking for a Python based solution as already use similar for my solar battery data. Would you mind sharing your method for extracting the past 3years of data from you Tado system with me please? I am not looking to change settings as detailed in @Equinoxefr example, as all I am looking for is the temp & humidity data..... but I am struggling to get the Python code started. Thanks, Matt

      Reply
      1. Matt says:

        @edent. I have run through all the instructions on you blog, and everything runs as it should. I am using a Windows Pc and simply run inside of command prompt.

        However what doesn't work is the very last step in your blog for 'Historic Information'. When I run this code (using all my details from previous steps and using a new/valid bearer) then the code runs, thinks for a second or two, and just seems to finish without outputting anything.....I am just presented with a new blank command line.

        Does the same still work for you or am I doing something wrong do you think? I am wondering how the temp/humidity data would be displayed.... as a bunch of line separate timestamped line items? As mentioned in my previous post to David, I am simply looking to download a recorded the last 1-2yrs worth of temp & humidity data from my Tado Heating Thermostat. Any help / guidance appreciated!

        Reply
        1. Matt says:

          @edent. OK so looks like this may be down to a syntax error in your given code. I think there needs to be " when you have shown as ' around 'Authorization: Bearer abc'

          No idea why this has changed and why the single equations work for other queries but the code that works for me for pulling historical data for a single date is:

          https://my.tado.com/api/v2/homes/123456/zones/1/dayReport?date=2018-02-14' -H "Authorization: Bearer abc"

          What I would love to know though, is how on earth you pull out the data for multiple days (or even a years worth of data). I see on your other post "two years worth of heating data" you attach the files and each day has its own json file. Are you happy to share the code on how to pull this info down please? That would be a great help as I have got as far as my limited abilities can get me for now... Thank you.

          Reply
        2. @edent says:

          @matt When I try the API call, it works. It gives me back a very large JSON file. You might need to tell your code to save the response to disk. There is an alternative though. If you log in to the Tado website, then open your browser's developer tools, and switch to the "network" tab - you should be able to see all the API calls that Tado makes. Open the Heating option and click on the graph. You should see today's data. Look in the network tab and you'll see the API call your browser makes. You can either copy the API call from there, or save the response to disk.

          Good luck!

          Reply

What links here from around this blog?

What are your reckons?

All comments are moderated and may not be published immediately. Your email address will not be published.Allowed HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong> <pre> <p> <br> <img src="" alt="" title="" srcset="">