How to get list of areas through websocket, API or hass object?

Hello,

I’m working on building my own custom dashboard using React.

I have 3 ways I can communicate to Home Assistant, the API, the hass object (from custom panel) and the websocket library.

However I can’t seem to figure out how to get a list of all my configured areas from any of these?

I currently have 5 areas configured

all of them have devices and entities.

I looked at all the entities and none of them have any area information?

e.g. here is my desk light entity which is tied to my “office” area:

{
    "entity_id": "light.desk_light",
    "state": "on",
    "attributes": {
        "min_mireds": 111,
        "max_mireds": 666,
        "effect_list": [
            "effect_colorloop",
            "effect_pulse",
            "effect_stop"
        ],
        "supported_color_modes": [
            "color_temp",
            "hs"
        ],
        "color_mode": "hs",
        "brightness": 255,
        "hs_color": [
            27.999,
            26
        ],
        "rgb_color": [
            255,
            219,
            188
        ],
        "xy_color": [
            0.392,
            0.358
        ],
        "icon": "mdi:led-strip-variant",
        "friendly_name": "Desk light",
        "supported_features": 55
    },
    "context": {
        "id": "0181178cb7301e244a98a5ae478af52c",
        "parent_id": null,
        "user_id": null
    },
    "last_changed": "2022-05-31T00:38:26.864Z",
    "last_updated": "2022-05-31T00:38:26.864Z"
}

So if there’s no “area_id” on entities, in either the hass object, the rest api to entities, or the websocket api to subscribeEntities, how do I get a list of areas and all entities / devices inside those areas?

I want to create a Dashboard with page that show all areas and cards for all entities in those areas.

PS. I’m using TypeScript for my project.

Related links.
Git pull request for this feature that was never merged :frowning:

Feature request for this feature that wasn’t responded to.

This file seems to be related somehow, but no documentation on how I could get this “config” from the websocket or rest api.

Closest thing to an answer I could find is this comment on github: https://github.com/home-assistant/core/pull/37376#issuecomment-653255510

but it doesn’t explain how that can be consumed with the websocket package :confused:

I found a workaround!

There doesn’t seem to be any way to get the area_registry list using either the hass object, the rest API or the official websocket package.

However if instead of using the proper package, you manually set up the websocket yourself, you can get the list of areas like this:

const socket = new WebSocket('ws://homeassistant.local:8123/api/websocket')
socket.onopen = function (event) {
    socket.send(
      JSON.stringify({
        type: 'auth',
        access_token: HOMEASSISTANT_TOKEN,
      })
    )
  }

// after you get the auth_ok message, send this websocket:
socket.send(JSON.stringify({ type: 'config/area_registry/list', id: 4 }))

and then you will get a response with areas!

I don’t understand why this isn’t part of the actual package. But at least there’s a workaround :sweat_smile:

4 Likes

Well played!

How did you find this hidden command? I would be interested in retrieving the device and entity registry vie the web socket…

1 Like

man you’re a real life saver, this worked perfectly!! I just had to add a line with “const WebSocket = require(‘ws’);” and run the command npm install ws and it worked. I also added the same for entity and device registry filtering to only appear the most important parameters such as entity_id’s or area_id’s. My code looks like this (note: replace “TOKEN” with your long-lived access token from home assistant):

const WebSocket = require(‘ws’);

const socket = new WebSocket(‘ws://YOURHOMEASSISTANTURL:8123/api/websocket’);

socket.onopen = function (event) {
socket.send(
JSON.stringify({
type: ‘auth’,
access_token: “TOKEN”,
})
);
};

socket.onmessage = function (event) {
const message = JSON.parse(event.data);
if (message.type === ‘auth_ok’) {
console.log(‘Authentication successful. Fetching area registry…’);
socket.send(JSON.stringify({ type: ‘config/area_registry/list’, id: 4 }));
}
else if (message.type === ‘result’ && message.id === 4)
{
console.log(’---------------------------------AREA REGISTRY-----------------------------------’)
message.result.forEach((item) => {
console.log(‘Area ID:’, item.area_id);
});
socket.send(JSON.stringify({ type: ‘config/device_registry/list’, id: 5 }));
}
else if (message.type === ‘result’ && message.id === 5)
{
console.log(’---------------------------------DEVICE REGISTRY-----------------------------------’)
message.result.forEach((item) => {
console.log(‘Area ID:’, item.area_id);
console.log(‘Manufacturer:’, item.manufacturer);
console.log(‘Model:’, item.model);
});
socket.send(JSON.stringify({ type: ‘config/entity_registry/list’, id: 6 }));

}
else if (message.type === ‘result’ && message.id === 6)
{
console.log(’---------------------------------ENTITY REGISTRY-----------------------------------’)
message.result.forEach((item) => {
console.log(‘Entity ID:’, item.entity_id);
});

socket.close();

}
};

socket.onclose = function (event) {
console.log(‘WebSocket connection closed.’);
};