Skip to content

Add WattWächter Plus integration#165238

Draft
smartcircuits wants to merge 3 commits intohome-assistant:devfrom
SmartCircuits-GmbH:add-wattwaechter-integration
Draft

Add WattWächter Plus integration#165238
smartcircuits wants to merge 3 commits intohome-assistant:devfrom
SmartCircuits-GmbH:add-wattwaechter-integration

Conversation

@smartcircuits
Copy link

@smartcircuits smartcircuits commented Mar 9, 2026

Summary

  • Add new integration for WattWächter Plus energy monitoring devices by SmartCircuits GmbH
  • Local polling via SML/OBIS protocol using aio-wattwaechter PyPI library
  • Supports zeroconf/mDNS discovery, config flow (manual + zeroconf + reauth + reconfigure), options flow for polling interval

Features

  • Dynamic sensor creation based on OBIS codes reported by the smart meter (energy, power, voltage, current, frequency, power factor)
  • Diagnostic sensors (WiFi signal, SSID, IP, firmware version, mDNS)
  • OTA firmware update entity with install progress tracking
  • MQTT conflict detection (prevents duplicate entities)
  • Diagnostics support with data redaction
  • Platinum quality scale

Quality

  • 31 tests covering config flow, sensor setup, update entity, and init
  • mypy --strict passes on all source files
  • Exception translations for all user-facing errors

Documentation

home-assistant/home-assistant.io#44004

Copilot AI review requested due to automatic review settings March 9, 2026 23:28
Copy link

@home-assistant home-assistant bot left a comment

Choose a reason for hiding this comment

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

Hi @tJpADUNCcs

It seems you haven't yet signed a CLA. Please do so here.

Once you do that we will be able to review and accept this pull request.

Thanks!

@home-assistant home-assistant bot marked this pull request as draft March 9, 2026 23:28
@home-assistant
Copy link

home-assistant bot commented Mar 9, 2026

Please take a look at the requested changes, and use the Ready for review button when you are done, thanks 👍

Learn more about our pull request process.

Copy link

@home-assistant home-assistant bot left a comment

Choose a reason for hiding this comment

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

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Adds a new core integration for WattWächter Plus energy monitoring devices (local polling + zeroconf discovery), including dynamic OBIS-based sensors, diagnostics support, and a firmware update entity.

Changes:

  • Introduces the wattwaechter integration (config flow, coordinator, sensors, update entity, diagnostics, translations/icons/branding).
  • Registers the integration for zeroconf discovery and generated integration metadata.
  • Adds a new test suite and CODEOWNERS entries for the integration.

Reviewed changes

Copilot reviewed 19 out of 25 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
homeassistant/components/wattwaechter/__init__.py Sets up the integration, creates client/coordinator, forwards platforms, handles options updates.
homeassistant/components/wattwaechter/config_flow.py Implements user/zeroconf flows plus reauth/reconfigure and options flow.
homeassistant/components/wattwaechter/const.py Defines domain/constants plus known OBIS and diagnostic sensor descriptions.
homeassistant/components/wattwaechter/coordinator.py Polls meter/system data via DataUpdateCoordinator and maps auth/connection errors.
homeassistant/components/wattwaechter/sensor.py Creates dynamic OBIS sensors + diagnostic sensors from coordinator data.
homeassistant/components/wattwaechter/update.py Adds firmware update entity with OTA check/install and reboot detection.
homeassistant/components/wattwaechter/entity.py Base entity providing device info (incl. configuration URL + MAC connection).
homeassistant/components/wattwaechter/diagnostics.py Implements diagnostics payload with token/MAC redaction.
homeassistant/components/wattwaechter/manifest.json Declares integration metadata, dependencies, requirements, and zeroconf type.
homeassistant/components/wattwaechter/strings.json Adds config/options/error/exception and entity translations.
homeassistant/components/wattwaechter/icons.json Adds entity icon translations.
homeassistant/components/wattwaechter/quality_scale.yaml Declares quality scale status for the integration.
homeassistant/components/wattwaechter/brand/icon.png Adds integration brand icon (256px).
homeassistant/components/wattwaechter/brand/icon@2x.png Adds integration brand icon (512px).
homeassistant/generated/zeroconf.py Registers _wattwaechter._tcp.local. zeroconf service mapping to the domain.
homeassistant/generated/integrations.json Adds generated integration registry entry for wattwaechter.
tests/components/wattwaechter/__init__.py Initializes the integration test package.
tests/components/wattwaechter/conftest.py Adds fixtures and test data for the new integration tests.
tests/components/wattwaechter/test_config_flow.py Tests config flow scenarios (user/zeroconf/reauth/reconfigure/options).
tests/components/wattwaechter/test_init.py Tests setup/unload and setup retry behavior.
tests/components/wattwaechter/test_sensor.py Tests OBIS sensor creation (known/unknown/minimal/no data) and diagnostics sensors.
tests/components/wattwaechter/test_update.py Tests update entity (no update/update available/install + error paths + reboot detection).
CODEOWNERS Adds codeowners for the new integration and its tests.

You can also share your feedback on Copilot code review. Take the survey.

"WattWächter device did not come back online after firmware update"
)
finally:
self._attr_in_progress = False
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

_attr_in_progress is used as a progress percentage for UpdateEntityFeature.PROGRESS (typically int | None). Setting it to False in the finally block leaves it as a boolean (and effectively 0), which can make the update appear perpetually “in progress” at 0%. Set it to None when the install is complete (and consider resetting to None on early failures too).

Suggested change
self._attr_in_progress = False
self._attr_in_progress = None

Copilot uses AI. Check for mistakes.
Comment on lines +11 to +30
from pytest_homeassistant_custom_component.common import MockConfigEntry

from aio_wattwaechter.models import (
AliveResponse,
InfoEntry,
MeterData,
ObisValue,
OtaCheckResponse,
OtaData,
SystemInfo,
)

from custom_components.wattwaechter.const import (
CONF_DEVICE_ID,
CONF_DEVICE_NAME,
CONF_FW_VERSION,
CONF_MAC,
CONF_MODEL,
DOMAIN,
)
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

These tests are importing/patching custom_components.wattwaechter.* and using pytest_homeassistant_custom_component fixtures, but this integration is implemented under homeassistant.components.wattwaechter. In core, tests should import from/patch homeassistant.components.wattwaechter.* and use tests.common.MockConfigEntry (and core fixtures) instead, otherwise the test suite won’t exercise the code under test.

Copilot uses AI. Check for mistakes.
Comment on lines +17 to +24
from custom_components.wattwaechter.const import (
CONF_DEVICE_ID,
CONF_DEVICE_NAME,
CONF_FW_VERSION,
CONF_MAC,
CONF_MODEL,
DOMAIN,
)
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

This test module imports custom_components.wattwaechter.* and patches custom_components.wattwaechter.config_flow.Wattwaechter, which won’t affect the real integration code at homeassistant.components.wattwaechter. Update imports/patch targets to homeassistant.components.wattwaechter.* so the tests actually cover the core integration.

Copilot uses AI. Check for mistakes.
Comment on lines +12 to +22
from custom_components.wattwaechter.coordinator import WattwaechterCoordinator

from .conftest import MOCK_ALIVE_RESPONSE, MOCK_METER_DATA, MOCK_SYSTEM_INFO


async def test_setup_entry(hass: HomeAssistant, mock_config_entry) -> None:
"""Test successful integration setup."""
with patch(
"custom_components.wattwaechter.Wattwaechter"
) as mock_cls:
client = mock_cls.return_value
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

This test patches custom_components.wattwaechter.Wattwaechter and imports the coordinator from custom_components.*, but the integration lives in homeassistant.components.wattwaechter. The patch target/imports should be updated to homeassistant.components.wattwaechter.* so the test suite is validating the actual core integration code.

Copilot uses AI. Check for mistakes.
Comment on lines +12 to +34
from custom_components.wattwaechter.const import DOMAIN

from .conftest import (
MOCK_ALIVE_RESPONSE,
MOCK_METER_DATA,
MOCK_METER_DATA_MINIMAL,
MOCK_METER_DATA_WITH_UNKNOWN,
MOCK_OTA_CHECK_NO_UPDATE,
MOCK_SYSTEM_INFO,
)


async def _setup_integration(hass: HomeAssistant, mock_config_entry, meter_data):
"""Set up the integration with given meter data."""
with patch(
"custom_components.wattwaechter.Wattwaechter"
) as mock_cls:
client = mock_cls.return_value
client.alive = AsyncMock(return_value=MOCK_ALIVE_RESPONSE)
client.meter_data = AsyncMock(return_value=meter_data)
client.system_info = AsyncMock(return_value=MOCK_SYSTEM_INFO)
client.ota_check = AsyncMock(return_value=MOCK_OTA_CHECK_NO_UPDATE)
client.host = "192.168.1.100"
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

This test imports DOMAIN from custom_components.wattwaechter.const and patches custom_components.wattwaechter.Wattwaechter. Since the integration is under homeassistant.components.wattwaechter, these imports/patches won’t target the code being shipped in core. Switch to homeassistant.components.wattwaechter.* throughout.

Copilot uses AI. Check for mistakes.
Comment on lines +29 to +31
with patch(
"custom_components.wattwaechter.Wattwaechter"
) as mock_cls:
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

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

This test patches custom_components.wattwaechter.* (including custom_components.wattwaechter.update.asyncio.sleep), but the integration is implemented at homeassistant.components.wattwaechter. Update the patch targets to homeassistant.components.wattwaechter.* so the test exercises the correct module and avoids false positives.

Copilot uses AI. Check for mistakes.
Add WattWächter Plus integration for local energy monitoring via SML/OBIS protocol.
@smartcircuits smartcircuits force-pushed the add-wattwaechter-integration branch from 0fef350 to d19d94d Compare March 9, 2026 23:35
Copy link

@home-assistant home-assistant bot left a comment

Choose a reason for hiding this comment

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

Hi @smartcircuits

It seems you haven't yet signed a CLA. Please do so here.

Once you do that we will be able to review and accept this pull request.

Thanks!

@smartcircuits
Copy link
Author

Addressed the Copilot feedback:

  • Fixed _attr_in_progress = FalseNone in update.py (1d78171)

Regarding the automated "single platform" comment: this integration provides sensor, update, and diagnostics. Happy to split update into a follow-up PR if required by reviewers.

The tests currently use custom_components.* imports (carried over from the custom component). I'll update them to homeassistant.components.wattwaechter.* once CI workflows are approved and I can verify against the core test runner.

Companion docs PR: home-assistant/home-assistant.io#44004

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants