RESTful sensor: Help with understanding

Hi,
I was trying to understand how to use this integration for my own education, but recently it has become more important as the core ‘Met office’ integration fails for a specific location on a daily basis and screwing up my automations).

When I call the URL, I can get either XML or JSON

XML:

<SiteRep>
<Wx>
<Param name="F" units="C">Feels Like Temperature</Param>
<Param name="G" units="mph">Wind Gust</Param>
<Param name="H" units="%">Screen Relative Humidity</Param>
<Param name="T" units="C">Temperature</Param>
<Param name="V" units="">Visibility</Param>
<Param name="D" units="compass">Wind Direction</Param>
<Param name="S" units="mph">Wind Speed</Param>
<Param name="U" units="">Max UV Index</Param>
<Param name="W" units="">Weather Type</Param>
<Param name="Pp" units="%">Precipitation Probability</Param>
</Wx>
<DV dataDate="2023-07-06T05:00:00Z" type="Forecast">
<Location i="354272" lat="51.7866" lon="-1.4807" name="WITNEY" country="ENGLAND" continent="EUROPE" elevation="79.0">
<Period type="Day" value="2023-07-06Z">
<Rep D="SW" F="10" G="20" H="89" Pp="1" S="4" T="11" V="GO" W="0" U="0">0</Rep>
<Rep D="SW" F="8" G="18" H="96" Pp="1" S="2" T="8" V="MO" W="0" U="0">180</Rep>
<Rep D="WSW" F="10" G="16" H="92" Pp="5" S="4" T="11" V="MO" W="7" U="1">360</Rep>
<Rep D="SW" F="15" G="16" H="66" Pp="6" S="9" T="17" V="VG" W="7" U="4">540</Rep>
<Rep D="SSW" F="17" G="18" H="51" Pp="6" S="11" T="19" V="VG" W="7" U="5">720</Rep>
<Rep D="SSW" F="17" G="25" H="50" Pp="5" S="13" T="20" V="VG" W="7" U="4">900</Rep>
<Rep D="SSW" F="16" G="25" H="46" Pp="0" S="13" T="19" V="VG" W="1" U="1">1080</Rep>
<Rep D="S" F="14" G="18" H="64" Pp="0" S="7" T="15" V="VG" W="0" U="0">1260</Rep>
</Period>
<Period type="Day" value="2023-07-07Z">
<Rep D="S" F="13" G="18" H="79" Pp="1" S="7" T="14" V="VG" W="0" U="0">0</Rep>
<Rep D="SSE" F="12" G="16" H="88" Pp="0" S="4" T="12" V="GO" W="0" U="0">180</Rep>
<Rep D="SE" F="14" G="13" H="82" Pp="0" S="4" T="14" V="GO" W="1" U="1">360</Rep>
<Rep D="SSE" F="19" G="11" H="58" Pp="0" S="7" T="20" V="VG" W="1" U="5">540</Rep>
<Rep D="SSE" F="23" G="18" H="45" Pp="0" S="9" T="24" V="VG" W="1" U="8">720</Rep>
<Rep D="S" F="24" G="18" H="39" Pp="0" S="11" T="26" V="VG" W="1" U="5">900</Rep>
<Rep D="SSE" F="23" G="16" H="44" Pp="0" S="9" T="25" V="VG" W="1" U="1">1080</Rep>
<Rep D="SE" F="19" G="13" H="66" Pp="0" S="4" T="19" V="VG" W="0" U="0">1260</Rep>
</Period>
<Period type="Day" value="2023-07-08Z">
<Rep D="E" F="17" G="16" H="69" Pp="0" S="7" T="18" V="VG" W="0" U="0">0</Rep>
<Rep D="ESE" F="17" G="18" H="71" Pp="3" S="9" T="18" V="VG" W="0" U="0">180</Rep>
<Rep D="SE" F="18" G="18" H="72" Pp="13" S="9" T="19" V="VG" W="7" U="1">360</Rep>
<Rep D="SSE" F="21" G="20" H="73" Pp="32" S="9" T="22" V="VG" W="10" U="3">540</Rep>
<Rep D="S" F="22" G="22" H="68" Pp="39" S="11" T="23" V="VG" W="10" U="6">720</Rep>
<Rep D="SSW" F="21" G="27" H="65" Pp="61" S="13" T="23" V="VG" W="14" U="4">900</Rep>
<Rep D="SSW" F="19" G="22" H="63" Pp="41" S="11" T="21" V="VG" W="10" U="1">1080</Rep>
<Rep D="SW" F="16" G="13" H="77" Pp="6" S="7" T="17" V="VG" W="0" U="0">1260</Rep>
</Period>
<Period type="Day" value="2023-07-09Z">
<Rep D="SW" F="14" G="11" H="86" Pp="2" S="7" T="14" V="VG" W="0" U="0">0</Rep>
<Rep D="SW" F="12" G="9" H="92" Pp="1" S="4" T="13" V="VG" W="0" U="0">180</Rep>
<Rep D="S" F="14" G="9" H="89" Pp="6" S="4" T="14" V="VG" W="7" U="1">360</Rep>
<Rep D="SSW" F="17" G="16" H="69" Pp="11" S="7" T="18" V="VG" W="7" U="5">540</Rep>
<Rep D="SSW" F="19" G="20" H="54" Pp="15" S="9" T="21" V="VG" W="7" U="6">720</Rep>
<Rep D="SSW" F="19" G="20" H="56" Pp="33" S="9" T="21" V="VG" W="10" U="3">900</Rep>
<Rep D="SW" F="18" G="16" H="66" Pp="34" S="7" T="19" V="VG" W="10" U="1">1080</Rep>
<Rep D="SSW" F="15" G="9" H="81" Pp="3" S="4" T="15" V="VG" W="0" U="0">1260</Rep>
</Period>
<Period type="Day" value="2023-07-10Z">
<Rep D="SSW" F="13" G="11" H="91" Pp="2" S="7" T="14" V="VG" W="0" U="0">0</Rep>
<Rep D="SSW" F="13" G="11" H="94" Pp="8" S="7" T="14" V="GO" W="2" U="0">180</Rep>
<Rep D="SSW" F="14" G="16" H="90" Pp="13" S="9" T="15" V="GO" W="7" U="1">360</Rep>
<Rep D="SSW" F="16" G="25" H="75" Pp="39" S="11" T="18" V="VG" W="10" U="3">540</Rep>
<Rep D="SSW" F="17" G="29" H="66" Pp="43" S="13" T="19" V="GO" W="10" U="6">720</Rep>
<Rep D="SW" F="17" G="29" H="65" Pp="42" S="13" T="20" V="GO" W="10" U="4">900</Rep>
<Rep D="SW" F="16" G="25" H="68" Pp="40" S="11" T="19" V="VG" W="10" U="1">1080</Rep>
<Rep D="SSW" F="15" G="18" H="80" Pp="6" S="9" T="16" V="VG" W="7" U="0">1260</Rep>
</Period>
</Location>
</DV>
</SiteRep>

JSON:

{"SiteRep":{"Wx":{"Param":[{"name":"F","units":"C","$":"Feels Like Temperature"},{"name":"G","units":"mph","$":"Wind Gust"},{"name":"H","units":"%","$":"Screen Relative Humidity"},{"name":"T","units":"C","$":"Temperature"},{"name":"V","units":"","$":"Visibility"},{"name":"D","units":"compass","$":"Wind Direction"},{"name":"S","units":"mph","$":"Wind Speed"},{"name":"U","units":"","$":"Max UV Index"},{"name":"W","units":"","$":"Weather Type"},{"name":"Pp","units":"%","$":"Precipitation Probability"}]},"DV":{"dataDate":"2023-07-06T05:00:00Z","type":"Forecast"}}}

I have created multiple versions of the sensor below, but cannot get it to work (based on the docs and lots of threads pin this forum). Honestly, I am utterly confused - I have no education in REST so am missing some basics which I assume the docs think I have.

In the examples below, I am trying to get a sensor value of D from the first Rep and also an attribute with the same info - just for my education.

rest:
- resource: http://datapoint.metoffice.gov.uk/public/data/val/wxfcs/all/xml/352086?res=3hourly&key=xxxxx
  scan_interval: 3600
  sensor:
    - name: weather_test
      value_template: "{{ value_json.Rep[0]['@D'] }}"
      json_attributes_path: "$.SiteRep.DV.Location.Period.Rep[0]"
      json_attributes:
        - "@D"
    - name: weather_test_2
      value_template: "OK"
      json_attributes_path: "$.SiteRep.DV.Location"
      json_attributes:
        - "Period"

weather_test produces a state of unknown and no attributes
weather_test_2 produces a sate of OK and an attribute array of all of Period.

Any pointers would be greatly appreciated as to whether I should be using the XML or JSON output and how to configure value_template, json_attributes and json_attributes_path.

Thanks.

I may have cracked the attribute with:

      json_attributes_path: "$.SiteRep.DV.Location.Period[0].Rep[0]"
      json_attributes:
        - "@D"

which produces @D: SW

…it was a long day yesterday, so perhaps this morning’s fresh start is helping!

Any thoughts on the value_template would still be greatly appreciated (and also appointer as to wether XML or JSON is preferred).

Probably personal preference, I use Json as i find it better documented and slightly more user friendly, dont know if you are aware but there are a couple of helpful tools for working out Json paths that may be helpful:

1 Like

Thanks for your reply!

A good night’s sleep followed by a cup of coffee has helped as I have worked out the value_template as well:

- resource: http://datapoint.metoffice.gov.uk/public/data/val/wxfcs/all/xml/352086?res=3hourly&key=xxxxx
  scan_interval: 3600
  sensor:
    - name: weather_test
      value_template: "{{ value_json['SiteRep']['DV']['Location']['Period'][0]['Rep'][0]['@D'] }}"
      json_attributes_path: "$.SiteRep.DV.Location.Period[0].Rep[0]"
      json_attributes:
        - "@D"
        - "@F"
        - "@G"
        - "@H"
        - "@Pp"
        - "@S"
        - "@T"
        - "@V"
        - "@W"
        - "@U"

Thanks for that - I’ll take a look.

If the URL outputs in JSON, are the following formatted any differently?

      value_template:
      json_attributes_path:
      json_attributes:

…another question.

This works:

- name: weather_test
  unique_id: weather_test_temp_rest
  value_template: "{{ value_json.SiteRep.DV.Location.Period[0].Rep[2]['@T'] }}"

But I want to replace the Rep[2] based on the time of day. I have the formula working in templates and, if this was a normal template, I’d do this (which doesn’t work here):

- name: weather_test
  unique_id: weather_test_temp_rest
  value_template: >
    {% set row = now().hour/3 |int -1 %}
    {{ value_json.SiteRep.DV.Location.Period[0].Rep[row]['@T'] }}

Any ideas?

ugh - my maths was wrong. If anyone comes across this, the correct answer is:

- name: Weather temp (rest)
  unique_id: weather_temp_rest
  value_template: >
    {% set row = (now().hour/3)|round(0) -1 %}
    {{ value_json.SiteRep.DV.Location.Period[0].Rep[row]['@T'] }}

OK, next question.

Can you also template json_attributes_path?

I have tried applying the same logic for value_template (which I recognise has the word template in it) to json_attributes_path which I recognise does not have the word template in it) as follows:

- name: Weather (rest)
  unique_id: weather_rest
  device_class: temperature
  unit_of_measurement: '°C'
  value_template: > # "{{ value_json.SiteRep.DV.Location.Period[0].Rep[0]['@D'] }}"
    {% set row = (now().hour/3)|round(0) -1 %}
    {{ value_json.SiteRep.DV.Location.Period[0].Rep[row]['@T'] }}
  json_attributes_path: > #"$.SiteRep.DV.Location.Period[0].Rep[0]"
    {% set row = (now().hour/3)|round(0) -1 %}
    $.SiteRep.DV.Location.Period[0].Rep[row]
  json_attributes:
    - "@D"
    - "@F"
    - "@G"
    - "@H"
    - "@Pp"
    - "@S"
    - "@T"
    - "@V"
    - "@W"
    - "@U"

I also tried variations on this, such as:

  json_attributes_path: > #"$.SiteRep.DV.Location.Period[0].Rep[0]"
    {% set row = (now().hour/3)|round(0) -1 %}
    $.SiteRep.DV.Location.Period[0].Rep[{{row}}]

and

  json_attributes_path: > #"$.SiteRep.DV.Location.Period[0].Rep[0]"
    {% set row = (now().hour/3)|round(0) -1 %}
    '$.SiteRep.DV.Location.Period[0].Rep['+{{row}}+']'

and

  json_attributes_path: > #"$.SiteRep.DV.Location.Period[0].Rep[0]"
    {% set row = (now().hour/3)|round(0) -1 %}
    '$.SiteRep.DV.Location.Period[0].Rep['{{row}}']'

Is it possible?