Add service integration.reload

Well, the top is a script, so you put that in scripts, or wherever you store scripts (I have it all in a package), the bottom is an input_select, so you put that, well, again, wherever you want, as long as its under the correct hierarchy…

1 Like

Sorry, am I missing something?
What is the point of the script and then an input_select?
I can simply go to the integrations page and click ‘reload’.
I’d like to be able to automate the ‘reload’ on a very regular basis (Ikea crappy integration needs reloading a lot)…
Thanks

To do it from the frontend and prevent exactly what you describe. As I wrote in the opening Fr :wink:

That is entirely possible, and has been all along.

Using node red?
Would be great to just ‘call’ a service? is this possible?

You can do it from node red. Since Node RED can make calls to the websockets API it can pull a list of all the config entries which includes their IDs. Then you can feed those ids into the service homeassistant.reload_config_entry.

I actually made a subflow I use that you might find handy for this. HA fires an event every time the device, entity or area registries change. It listens for those events (as well as the reconnect event after an HA or Node RED restart) and caches the corresponding registry (or registries) in the homeassistant global under homeassistant.config. Then you an easily filter through that data to find the integration you want, pull its ID and pass it into homeassistant.reload_config_entry whenever you need to:

[{"id":"16fdbd81.9d9b82","type":"subflow","name":"Store HA config","info":"Keep config of HA up to date and easily accessible in globals. That includes:\n\n- Config entries\n- Areas\n- Devices\n- Entities\n\nIt also flattens areas into entities. So any time devices or areas are updated it also updates entities by filling out their `area_id` field. Normally entities have this blank and instead expect the device to set the area.","category":"","in":[{"x":160,"y":40,"wires":[{"id":"b09b8d39.fe41e"},{"id":"bd3c0c61.c6069"},{"id":"9349652e.f4a0c"}]}],"out":[{"x":1120,"y":160,"wires":[{"id":"447143e7.58fbf4","port":0}]}],"env":[],"color":"#DDAA99","status":{"x":240,"y":360,"wires":[{"id":"4e6fd6ff.adeda8","port":0}]}},{"id":"7b548b89.a5c924","type":"ha-api","z":"16fdbd81.9d9b82","name":"Areas","server":"cc03735a.94933","debugenabled":false,"protocol":"websocket","method":"get","path":"","data":"{\"type\":\"config/area_registry/list\"}","dataType":"json","location":"payload.areas","locationType":"msg","responseType":"json","x":370,"y":160,"wires":[["447143e7.58fbf4"]]},{"id":"bd3c0c61.c6069","type":"ha-api","z":"16fdbd81.9d9b82","name":"Devices","server":"cc03735a.94933","debugenabled":false,"protocol":"websocket","method":"get","path":"","data":"{\"type\":\"config/device_registry/list\"}","dataType":"json","location":"payload","locationType":"msg","responseType":"json","x":320,"y":220,"wires":[["e9500159.2c764"]]},{"id":"b09b8d39.fe41e","type":"ha-api","z":"16fdbd81.9d9b82","name":"Entities","server":"cc03735a.94933","debugenabled":false,"protocol":"websocket","method":"get","path":"","data":"{\"type\":\"config/entity_registry/list\"}","dataType":"json","location":"payload","locationType":"msg","responseType":"json","x":320,"y":280,"wires":[["418cca4a.cbe594"]]},{"id":"dc8fe39c.fde6d8","type":"ha-api","z":"16fdbd81.9d9b82","name":"Config entries","server":"cc03735a.94933","debugenabled":false,"protocol":"http","method":"get","path":"/api/config/config_entries/entry","data":"{}","dataType":"json","location":"payload.entries","locationType":"msg","responseType":"json","x":760,"y":220,"wires":[["447143e7.58fbf4"]]},{"id":"2c4c713b.bb30ae","type":"server-events","z":"16fdbd81.9d9b82","name":"Entity reg updated","server":"cc03735a.94933","event_type":"entity_registry_updated","exposeToHomeAssistant":false,"haConfig":[{"property":"name","value":""},{"property":"icon","value":""}],"waitForRunning":true,"x":110,"y":280,"wires":[["b09b8d39.fe41e"]]},{"id":"9633cbe3.e13cd8","type":"server-events","z":"16fdbd81.9d9b82","name":"Device reg updated","server":"cc03735a.94933","event_type":"device_registry_updated","exposeToHomeAssistant":false,"haConfig":[{"property":"name","value":""},{"property":"icon","value":""}],"waitForRunning":true,"x":110,"y":220,"wires":[["bd3c0c61.c6069"]]},{"id":"1f22fbb3.0144d4","type":"server-events","z":"16fdbd81.9d9b82","name":"Area reg updated","server":"cc03735a.94933","event_type":"area_registry_updated","exposeToHomeAssistant":false,"haConfig":[{"property":"name","value":""},{"property":"icon","value":""}],"waitForRunning":true,"x":100,"y":160,"wires":[["9349652e.f4a0c"]]},{"id":"447143e7.58fbf4","type":"function","z":"16fdbd81.9d9b82","name":"Update global","func":"const data = msg.payload;\n\nif(data.entries){\n    update_config_entries(data.entries);\n    node.status({text:`Updated config entries (${data.entries.length})`});\n}\nif(data.areas){\n    update_areas(data.areas);\n    node.status({text:`Updated areas (${data.areas.length})`});\n}\nif(data.devices){\n    update_devices(data.devices);\n    node.status({text:`Updated devices (${data.devices.length})`});\n}\nif(data.entities){\n    update_entities(data.entities);\n    node.status({text:`Updated entities (${data.entities.length})`});\n}\n\nreturn msg;\n\nfunction update_entities(entities){\n    if(!entities){\n        entities = global.get('homeassistant.config.entities') || [];\n    }\n    \n    devices = global.get('homeassistant.config.entities');\n    for (let e of entities){\n        if(!e.area_id && e.device_id){\n            e.area_id = devices.find(d => d.id == e.device_id) || null;\n        }\n    }\n    \n    global.set('homeassistant.config.entities', entities);\n}\n\nfunction update_devices(devices){\n    global.set('homeassistant.config.devices', devices);\n    update_entities();\n}\n\nfunction update_areas(areas){\n    global.set('homeassistant.config.areas', areas);\n    update_entities();\n}\n\nfunction update_config_entries(entries){\n    global.set('homeassistant.config.entries', entries);\n}","outputs":1,"noerr":0,"initialize":"","finalize":"","x":1000,"y":160,"wires":[[]]},{"id":"fc6ceac.c313e98","type":"join","z":"16fdbd81.9d9b82","name":"Make payload","mode":"custom","build":"object","property":"payload","propertyType":"msg","key":"topic","joiner":"\\n","joinerType":"str","accumulate":false,"timeout":"1","count":"","reduceRight":false,"reduceExp":"","reduceInit":"","reduceInitType":"","reduceFixup":"","x":580,"y":220,"wires":[["dc8fe39c.fde6d8"]]},{"id":"e9500159.2c764","type":"change","z":"16fdbd81.9d9b82","name":"Set topic","rules":[{"t":"set","p":"topic","pt":"msg","to":"devices","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":415,"y":220,"wires":[["fc6ceac.c313e98"]],"l":false},{"id":"418cca4a.cbe594","type":"change","z":"16fdbd81.9d9b82","name":"Set topic","rules":[{"t":"set","p":"topic","pt":"msg","to":"entities","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":415,"y":280,"wires":[["fc6ceac.c313e98"]],"l":false},{"id":"4e6fd6ff.adeda8","type":"status","z":"16fdbd81.9d9b82","name":"","scope":["447143e7.58fbf4"],"x":140,"y":360,"wires":[[]]},{"id":"9349652e.f4a0c","type":"change","z":"16fdbd81.9d9b82","name":"Clear payload","rules":[{"t":"set","p":"payload","pt":"msg","to":"{}","tot":"json"}],"action":"","property":"","from":"","to":"","reg":false,"x":275,"y":160,"wires":[["7b548b89.a5c924"]],"l":false},{"id":"e44a4a26.6bef2","type":"server-events","z":"16fdbd81.9d9b82","name":"HA client","server":"cc03735a.94933","event_type":"home_assistant_client","exposeToHomeAssistant":false,"haConfig":[{"property":"name","value":""},{"property":"icon","value":""}],"waitForRunning":true,"x":80,"y":100,"wires":[["2a46ac.c8a18954"]]},{"id":"2a46ac.c8a18954","type":"switch","z":"16fdbd81.9d9b82","name":"Connected event","property":"payload","propertyType":"msg","rules":[{"t":"eq","v":"connected","vt":"str"}],"checkall":"true","repair":false,"outputs":1,"x":175,"y":100,"wires":[["b09b8d39.fe41e","bd3c0c61.c6069","9349652e.f4a0c"]],"l":false},{"id":"cc03735a.94933","type":"server","name":"Home Assistant","legacy":false,"addon":true,"rejectUnauthorizedCerts":true,"ha_boolean":"y|yes|true|on|home|open","connectionDelay":true,"cacheJson":true},{"id":"61f1c6b.d44ccb8","type":"inject","z":"a74fee2d.ac9068","name":"Manual","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":870,"y":1260,"wires":[["5ed06966.73fa48"]]},{"id":"5ed06966.73fa48","type":"subflow:16fdbd81.9d9b82","z":"a74fee2d.ac9068","name":"","env":[],"x":1020,"y":1260,"wires":[[]]}]

Looks like this once its going:
Screen Shot 2021-05-03 at 9.29.24 AM

Unfortunately its not as easy to get at this information without node RED since its only available in the websockets API and HA doesn’t have a websockets sensor, only a REST one. Although you could make a command_line sensor that uses jq to pick apart the files in .storage to find the information you wanted and store it in a sensor for reuse in automations. Then you wouldn’t have to make a map of names to IDs manually like Marius is showing above.

EDIT: Scratch this last part (mostly). Going back through my node red flow I remembered that config entries are weird, they don’t follow the normal registry pattern. There is a REST API for those, /api/config/config_entries/entry. So you actually could make a REST sensor that contains all the config entries.

If you need device, entity or area information though then you’re stuck with a command line sensor + jq on files in .storage. Those are only accessible over the websockets API by sending the command

{
  "type":"config/<area|device|entity>_registry/list"
}
1 Like

I’m using the official (as in not in Supervisor, not in HACS) Samsung TV integration, but it regularly gets out of sync with the tv and says it (the tv) is unavailable… what would I have to add to the Node Red flow to reload the integration if the TV is seen as unavailable?

1 Like

you need to check the GitHub issue tracker, because there are a few issues on that integration… No reload service will help you out until those have been resolved

I got the reloading part working but for some reason, the automation never triggers. Have you experienced anything like this? I even tried it in node red …
image

How did you get the reloading part to work?

Mine is for a different integration…

UPDATE 02/16/23: There is an updated simpler way doing this that I posted here: Add service integration.reload - #160 by skynet01

OLD WAY:

but it does work if I manually trigger it

Set up automation like this:

- id: auto_reload_emporia
  alias: "Keep Emporia running" 
  mode: single
  description: 'Check if Emporia is down'
  trigger:
  - platform: state
    entity_id: sensor.power_av_closet_6 # use any entity that is an emporia device / channel 
    to: unavailable
    for: 00:05:00
  - platform: template #check if any sensor gets stuck on the same number for 10 min
    value_template: "{{ as_timestamp( utcnow() ) | int > as_timestamp( states.sensor.power_pelican_123.last_changed ) | int + 10*60 }}"
  condition: []
  action:
  - service: rest_command.reload_emporia
    data: {}

Then in your main config file

rest_command:
  reload_emporia:
    url: http://[IP]:8123/api/config/config_entries/entry/[entry_id]/reload 
    method: POST
    headers:
      authorization: 'Bearer [Long-Lived Access Token]'
      content-type: 'application/json'
  1. [IP] = home assistant ip
  2. [entry_id] = go to config/.storage/core.config_entries search for emporia_vue you will see entry_id as the first record
  3. [Long Lived Access Token:] = Token can be created in the HA menu under your instance name. Yes there is a space between Bearer and the actual token
5 Likes

the whole idea behind this thread was the reload function, so you should not need/use the rest_command at all, and instead be using homeassistant.reload_config_entry service

2 Likes

Just need to verify, what’s the proper way of placing the long live access token?

rest_command:
  reload_aqara:
    url: http://192.168.1.40:8123/api/config/config_entries/entry/62dbc0b5edd9b3026b9078d199cb335c/reload 
    method: POST
    headers:
      authorization: eyJ0eXAiOiJblablalongaccesscode
      content-type: application/json

So it should it be like this?

rest_command:
  reload_aqara:
    url: http://192.168.1.40:8123/api/config/config_entries/entry/62dbc0b5edd9b3026b9078d199cb335c/reload 
    method: POST
    headers:
      authorization: 'Bearer eyJ0eXAiOiJblablalongaccesscode'
      content-type: application/json

hi @Mariusthvdb for the lovelace ui code, how do you key in for the rest of integration logo in your list other than ‘Luftdaten’ & ‘Philips’?

It should be like the second example with the word Bearer and a space before the token

homeassistant.reload_config_entry does not allow you to reload integrations that’s why rest_command is needed.

it allows you to reload config entries. which are integrations you setup via the UI config.

1 Like

Welp… you were right, thanks for telling me about this. I guess you just reference an entity to this service and it will automatically reload the automation that’s connected to it. Pretty sweet!

only thing you’ve got to remember is that when an integration has more entries, you have to reload those individually

Schermafbeelding 2021-09-06 om 09.43.53

just like you would have to do in the UI (click the entry, click 3 dots, and then click reload )

I’d LOVE to have this.
Some integrations would just stop working at some point and manually reloading is almost the solution to everyone of em.But having a nice automation to do this for me would be a much nicer touch.

Thank you guys.

This is already supported use " homeassistant.reload_config_entry" command, give it an entity that’s connected to an integration and integration will be reloaded