This document provides guidance for AI coding agents working on this Home Assistant custom integration project.
This is a Home Assistant custom component for the Israel Electric Corporation (IEC) API. It provides sensors and binary sensors for monitoring electricity consumption, invoices, and meter readings.
Integration details:
- Domain:
iec - Title: IEC (Israel Electric Corporation)
- Repository: GuyKh/iec-custom-component
Key directories:
custom_components/iec/- Main integration codeconfig/- Home Assistant configuration for local testing.github/workflows/- CI/CD workflows
- Python: 3.12+
- Home Assistant: 2025.1.4+
- iec-api: 0.5.4 (Python client for IEC API)
- Linting: ruff (with Home Assistant rules)
- Type Checking: mypy
custom_components/iec/
├── __init__.py # Integration entry point (async_setup_entry, async_unload_entry)
├── const.py # Constants and DOMAIN definitions
├── config_flow.py # UI configuration flow
├── coordinator.py # DataUpdateCoordinator - main API logic
├── commons.py # Shared utilities (timezone, helpers)
├── sensor.py # Sensor platform
├── binary_sensor.py # Binary sensor platform
├── iec_entity.py # Base entity class
└── services.yaml # Service definitions
Always use the project's scripts — do NOT craft your own hass, pip, or similar commands. The scripts handle environment setup correctly.
Setup:
./scripts/setup # Install dependenciesStart Home Assistant:
./scripts/develop # Start HA development environmentDebugging:
Enable debug logging in config/configuration.yaml:
logger:
default: info
logs:
custom_components.iec: debug
iec_api: debugReading logs:
- Terminal where
./script/developruns config/home-assistant.log
When starting a new task, always ask the user first:
- Should I switch to
mainbranch and rebase? - Or should I work from the current branch?
Then checkout a new feature branch before beginning work. Never work directly on main or stale branches.
- Features:
feature/description - Bug fixes:
fix/description - Documentation:
docs/description
Python:
- 4 spaces indentation
- 120 character lines
- Double quotes for strings
- Full type hints (mypy strict)
- Async for all I/O operations
- Follow ruff rules from
.ruff.toml
Validation commands:
./scripts/lint # Run ruff linter (auto-fixes where possible)- Uses
ConfigEntryfor UI-based configuration - Supports multiple accounts (one entry per account)
- Registers
PLATFORMS:sensorandbinary_sensor
IecApiCoordinatorextendsDataUpdateCoordinator- Handles all API calls to IEC
- Manages JWT tokens and authentication
- Stores data in
hass.data[DOMAIN][entry.entry_id] - Entities → Coordinator → API Client (never skip layers)
- Raise
ConfigEntryAuthFailed(triggers reauth) orUpdateFailed(retry)
- Base
IecEntityclass iniec_entity.py - Entities inherit from
CoordinatorEntity[IecApiCoordinator] - Read from
coordinator.data, never call API directly - Use
EntityDescriptiondataclasses for static entity metadata
- Implement in
config_flow.py - Support user setup, reauth
- Always set
unique_idfor entries
- Domain:
iec - Class prefix:
Iec
- Contracts: Electrical contracts linked to user account
- Meters: Physical meters associated with contracts
- Invoices: Billing information (consumption, amount, payment status)
- Meter Readings: Daily/hourly consumption data from smart meters
- Future Consumption: Predicted consumption based on historical data
- All constants defined in
const.py - Use
DOMAIN = "iec"for all domain references - Prefix IEC-specific classes with
Iec
JWT_DICT_NAME= "jwt"STATIC_DICT_NAME= "statics"ATTRIBUTES_DICT_NAME= "entity_attributes"ESTIMATED_BILL_DICT_NAME= "estimated_bill"INVOICE_DICT_NAME= "invoice"CONTRACT_DICT_NAME= "contract"DAILY_READINGS_DICT_NAME= "daily_readings"FUTURE_CONSUMPTIONS_DICT_NAME= "future_consumption"
- Add constants to
const.pyif needed - Add sensor logic in
sensor.py - Follow existing sensor patterns (base entity → specific sensor)
- Add full type annotations (mypy strict)
- Use
EntityDescriptiondataclass for static metadata
- Add constants to
const.pyif needed - Add binary sensor logic in
binary_sensor.py - Follow existing patterns
- Add full type annotations
When iec-api updates:
- Update version in
requirements.txt - Run type check to find breaking changes
- Update types as needed in
coordinator.py
After every code change, run:
ruff check .
ruff format .Before committing, run:
./scripts/lint # Auto-format and fix linting issuesConfigured tools:
- Ruff - Fast Python linter and formatter
- mypy - Static type checker (strict mode)
When first attempt validation fails:
- First attempt - Fix the specific error reported by the tool
- Second attempt - If it fails again, reconsider your approach
- Third attempt - If still failing, stop and ask for clarification
After ~10 file reads, you must either:
- Proceed with implementation based on available context
- Ask the developer specific questions about what's unclear
Tests are run via GitHub Actions workflows:
.github/workflows/lint.yml- Ruff linting.github/workflows/validate.yml- Full validation (ruff + mypy)
Always warn the developer before making changes that:
- Change entity IDs or unique IDs (users' automations will break)
- Modify config entry data structure (existing installations will fail)
- Change state values or attributes format (dashboards affected)
- Alter service call signatures (user scripts will break)
- Remove or rename config options
How to warn:
"This change will modify the entity ID format. Existing users' automations and dashboards will break. Should I proceed, or would you prefer a migration path?"
Follow Home Assistant patterns:
- Use type annotations (mypy strict)
- Follow ruff rules
- Add docstrings to public functions
- Use Home Assistant constants from
homeassistant.const - Implement proper error handling
- Use
async_redact_data()for sensitive data in diagnostics