Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Rointe integration #83069

Closed
wants to merge 4 commits into from
Closed

Conversation

tggm
Copy link

@tggm tggm commented Dec 1, 2022

Proposed change

This integration provides support for electrical radiators manufactured by Rointe. This is an initial implementation that supports some of Rointe's products:

  • D-Series Radiator
  • Towel Rails
  • Thermostat.

Type of change

  • Dependency upgrade
  • Bugfix (non-breaking change which fixes an issue)
  • New integration (thank you!)
  • New feature (which adds functionality to an existing integration)
  • Deprecation (breaking change to happen in the future)
  • Breaking change (fix/feature causing existing functionality to break)
  • Code quality improvements to existing code or addition of tests

Additional information

The integration uses cloud polling via a REST API owned by Rointe. Config flow requires the user to login to the API and then select which particular installation they want to add to HA.

It's currently available via HACS on https://github.com/tggm/rointe-hacs/

Checklist

  • The code change is tested and works locally.
  • Local tests pass. Your PR cannot be merged unless tests pass
  • There is no commented out code in this PR.
  • I have followed the development checklist
  • The code has been formatted using Black (black --fast homeassistant tests)
  • Tests have been added to verify that the new code works.

If user exposed functionality or configuration variables are added/changed:

If the code communicates with devices, web services, or third-party tools:

  • The manifest file has all fields filled out correctly.
    Updated and included derived files by running: python3 -m script.hassfest.
  • New or updated dependencies have been added to requirements_all.txt.
    Updated by running python3 -m script.gen_requirements_all.
  • For the updated dependencies - a link to the changelog, or at minimum a diff between library versions is added to the PR description.
  • Untested files have been added to .coveragerc.

To help with the load of incoming pull requests:

@tggm tggm force-pushed the rointe-integration branch 2 times, most recently from 50fe6fc to b73e3af Compare December 1, 2022 21:11
@tggm tggm marked this pull request as ready for review December 3, 2022 17:46
@tggm tggm force-pushed the rointe-integration branch from 8043d3e to 30e8cce Compare December 6, 2022 19:37
homeassistant/components/rointe/const.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/rointe_entity.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
@tggm
Copy link
Author

tggm commented Dec 6, 2022

Thank you for the first look at this @bachya. It was indeed in a very rough state. I cleaned some of the issue and will ping you when I manage to clear the rest.

This latest commit contains a reauth flow I've been working. It also contains a bunch of debug statements which I added to help another user setup this integration (it's currently available via HACS so I have a couple of people beta testing this).

@bachya
Copy link
Contributor

bachya commented Dec 6, 2022

This latest commit contains a reauth flow I've been working. It also contains a bunch of debug statements which I added to help another user setup this integration (it's currently available via HACS so I have a couple of people beta testing this).

Per my previous comment, I would recommend that you do a reauth flow in a separate PR—this PR already has plenty in it.

@tggm
Copy link
Author

tggm commented Dec 6, 2022

Per my previous comment, I would recommend that you do a reauth flow in a separate PR—this PR already has plenty in it.

Will do.

@tggm tggm force-pushed the rointe-integration branch from cf88d69 to e8e09ee Compare December 7, 2022 13:52
@tggm
Copy link
Author

tggm commented Dec 7, 2022

@bachya I cleared up the issues. I changed async_unload_entry a bit and during testing I noticed that when removing the integration and then adding it again the entities do not show up (shown as unavailable). They do however appear after rebooting HASS.

No errors, everything appears OK in logs, both removing and adding again. Maybe async_unload_entry is still not correct

@tggm
Copy link
Author

tggm commented Dec 7, 2022

@bachya I fixed the problem with unloading the integration. It was a stupid error where I was using a class variable to store my entities.

I also updated the code to use async_forward_entry_setups() according to this post

Finally I removed some useless code from async_unload_entry that I'd copied from another integration.

@tggm tggm requested a review from bachya December 8, 2022 17:21
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/coordinator.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/config_flow.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/config_flow.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/config_flow.py Outdated Show resolved Hide resolved
@tggm tggm force-pushed the rointe-integration branch from 35594e7 to 5a3720b Compare December 9, 2022 17:08
@tggm tggm requested a review from bachya December 9, 2022 17:12
Copy link
Contributor

@bachya bachya left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're doing great—keep going!

homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/device_manager.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/device_manager.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/device_manager.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor.py Outdated Show resolved Hide resolved
@tggm tggm force-pushed the rointe-integration branch from f0098d1 to e394f72 Compare December 10, 2022 09:52
@tggm tggm requested a review from bachya December 10, 2022 10:24
@tggm
Copy link
Author

tggm commented Dec 15, 2022

Hi @bachya,

Are there any other tasks you want me to work to help with the review?

homeassistant/components/rointe/__init__.py Show resolved Hide resolved
homeassistant/components/rointe/__init__.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/const.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/sensor_descriptions.py Outdated Show resolved Hide resolved
tests/components/rointe/test_config_flow.py Outdated Show resolved Hide resolved
@bachya bachya changed the title Rointe integration Add Rointe integration Dec 15, 2022
@tggm tggm force-pushed the rointe-integration branch 2 times, most recently from fd36f0c to 6639879 Compare December 18, 2022 11:51
@tggm tggm requested a review from bachya December 18, 2022 11:57
@tggm
Copy link
Author

tggm commented Dec 18, 2022

What are the test coverage targets for files other than config_flow.py ?

@bachya
Copy link
Contributor

bachya commented Dec 18, 2022

What are the test coverage targets for files other than config_flow.py ?

Depends on your objective. Config flow tests are required; (almost) everything else is discretionary.

More info: https://developers.home-assistant.io/docs/integration_quality_scale_index?_highlight=coverage#gold-

Copy link
Member

@gjohansson-ST gjohansson-ST left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

First pass for cleanups.
Please rebase after the cleanups.

homeassistant/components/rointe/.gitignore Outdated Show resolved Hide resolved
homeassistant/components/rointe/const.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/coordinator.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/manifest.json Outdated Show resolved Hide resolved
homeassistant/components/rointe/rointe_entity.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/translations/en.json Outdated Show resolved Hide resolved
@home-assistant home-assistant bot marked this pull request as draft September 26, 2023 07:26
@tggm tggm force-pushed the rointe-integration branch from b3ee8d2 to 7fba29c Compare September 26, 2023 13:06
@tggm tggm requested a review from gjohansson-ST September 27, 2023 21:03
@tggm tggm marked this pull request as ready for review October 5, 2023 09:33
homeassistant/components/rointe/climate.py Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/entity.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/entity.py Outdated Show resolved Hide resolved
@home-assistant home-assistant bot marked this pull request as draft November 22, 2023 20:29
@tggm tggm force-pushed the rointe-integration branch 2 times, most recently from 8e7d96e to 20936eb Compare December 24, 2023 17:53
@tggm tggm requested a review from emontnemery December 24, 2023 17:54
@tggm tggm marked this pull request as ready for review December 29, 2023 22:52
@tggm tggm force-pushed the rointe-integration branch from e0b6f79 to 7a80011 Compare December 30, 2023 00:35
@MartinHjelmare MartinHjelmare marked this pull request as draft December 30, 2023 00:40
@tggm tggm marked this pull request as ready for review December 30, 2023 18:15
@tggm tggm requested a review from MartinHjelmare December 30, 2023 18:15
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/climate.py Outdated Show resolved Hide resolved
homeassistant/components/rointe/config_flow.py Outdated Show resolved Hide resolved

async def async_step_installation(
self, user_input: dict[str, Any] | None
) -> FlowResult:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Okay so apparently 1 account can lead to more installations? Can you maybe elaborate on what an installation is? Usually we have the guideline that 1 (cloud) account = 1 config entry.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Essentially it represents a house/home. It's part of their hierarchy: Installations -> Zones -> Devices.

During configuration the user must pick one installation (for the majority of cases there will only be one option available). The Installation ID is then stored as it is required to retrieve devices.

homeassistant/components/rointe/config_flow.py Outdated Show resolved Hide resolved
update_interval=ROINTE_API_REFRESH_INTERVAL,
)

self.unregistered_keys = {platform: {} for platform in PLATFORMS}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What's a key?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In that context a "key" is the unique identifier of each device. It's determined by the manufacturer's API

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

By the way, do you have discord? Can you maybe pop me a message? (@joostlek)

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
self.unregistered_keys = {platform: {} for platform in PLATFORMS}

@home-assistant home-assistant bot marked this pull request as draft January 2, 2024 08:53
@tggm tggm requested a review from joostlek January 2, 2024 19:28
self, user_input: dict[str, Any] | None = None
) -> FlowResult:
"""Select the installation."""
if not user_input or CONF_INSTALLATION not in user_input:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
if not user_input or CONF_INSTALLATION not in user_input:
if not user_input:

data_schema=vol.Schema(
{
vol.Required(CONF_INSTALLATION): vol.In(
self.step_user_installations
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What will be fetched? Do we now only show a list of random numbers or can we also get a list of names with the installation id? This way it can be more user friendly since we can pass a name/value pair

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There will be a list of names yes. Each installation has a name. Example:

image

update_interval=ROINTE_API_REFRESH_INTERVAL,
)

self.unregistered_keys = {platform: {} for platform in PLATFORMS}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

By the way, do you have discord? Can you maybe pop me a message? (@joostlek)

update_interval=ROINTE_API_REFRESH_INTERVAL,
)

self.unregistered_keys = {platform: {} for platform in PLATFORMS}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
self.unregistered_keys = {platform: {} for platform in PLATFORMS}

Comment on lines +41 to +56

new_devices = await self.device_manager.update()

for platform in PLATFORMS:
self.unregistered_keys[platform].update(
{
device_id: device
for device_id, device in new_devices.items()
if device_id not in self.unregistered_keys[platform]
}
)

for device in new_devices.values():
device_update_info(self.hass, device)

return new_devices
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
new_devices = await self.device_manager.update()
for platform in PLATFORMS:
self.unregistered_keys[platform].update(
{
device_id: device
for device_id, device in new_devices.items()
if device_id not in self.unregistered_keys[platform]
}
)
for device in new_devices.values():
device_update_info(self.hass, device)
return new_devices
return await self.device_manager.update()

Comment on lines +90 to +105


@callback
def device_update_info(hass: HomeAssistant, rointe_device: RointeDevice) -> None:
"""Update device registry info."""

LOGGER.debug("Updating device registry info for %s", rointe_device.name)

dev_registry = dr.async_get(hass)

if device := dev_registry.async_get_device(
identifiers={(DOMAIN, rointe_device.id)},
):
dev_registry.async_update_device(
device.id, sw_version=rointe_device.firmware_version
)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
@callback
def device_update_info(hass: HomeAssistant, rointe_device: RointeDevice) -> None:
"""Update device registry info."""
LOGGER.debug("Updating device registry info for %s", rointe_device.name)
dev_registry = dr.async_get(hass)
if device := dev_registry.async_get_device(
identifiers={(DOMAIN, rointe_device.id)},
):
dev_registry.async_update_device(
device.id, sw_version=rointe_device.firmware_version
)

homeassistant/components/rointe/climate.py Show resolved Hide resolved
@MartinHjelmare MartinHjelmare removed their request for review February 3, 2024 06:55
Copy link

github-actions bot commented Apr 4, 2024

There hasn't been any activity on this pull request recently. This pull request has been automatically marked as stale because of that and will be closed if no further activity occurs within 7 days.
If you are the author of this PR, please leave a comment if you want to keep it open. Also, please rebase your PR onto the latest dev branch to ensure that it's up to date with the latest changes.
Thank you for your contribution!

@github-actions github-actions bot added the stale label Apr 4, 2024
@github-actions github-actions bot closed this Apr 11, 2024
@github-actions github-actions bot locked and limited conversation to collaborators Apr 12, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants