Check Energa Operator power outages by GPS coordinates or address
Reason this release was yanked:
wrong versioning
Project description
energa-outages-api
Python library for checking Energa Operator planned and emergency power outages. Supports lookup by GPS coordinates or postal address.
pip install energa-outages-api
from energa_outages_api import EnergaOutagesClient
Features
- Live data from Energa Operator API (northern/central Poland)
- Check outages by GPS coordinates with configurable margin radius and confidence scoring
- Check outages by address (city, street, building number) with prefix normalization
- Async-first (
aiohttp), with a sync wrapper for scripts - Built-in TTL cache (default 5 min) — safe to call on every HA update cycle
- Zero dependencies beyond
aiohttp - Fully typed, PEP 561 compliant
Installation
pip install energa-outages-api
From GitHub:
pip install git+https://github.com/vincentto13/energa-outages-api.git
Requires Python 3.11+.
Quick start
Check by GPS coordinates
import asyncio
from energa_outages_api import EnergaOutagesClient
async def main():
async with EnergaOutagesClient() as client:
match = await client.check_location(lat=54.352, lon=18.647, margin_m=200)
if match:
print(f"Outage detected! Confidence: {match.confidence:.0%}")
print(f"Region: {match.shutdown.region_name}")
print(f"Window: {match.shutdown.start_date} → {match.shutdown.end_date}")
else:
print("No outage at your location.")
asyncio.run(main())
Check by address
async def main():
async with EnergaOutagesClient() as client:
matches = await client.check_address(
city="Włocławek",
street="ul. Grodzka", # "ul." prefix stripped automatically
number="169",
)
for m in matches:
print(f"{m.matched_address} [{m.confidence:.0%}]")
print(f" {m.shutdown.start_date} → {m.shutdown.end_date}")
Sync usage
from energa_outages_api import EnergaOutagesClientSync
with EnergaOutagesClientSync() as client:
match = client.check_location(lat=54.352, lon=18.647)
matches = client.check_address(city="Gdańsk", street="Dworska", number="11")
API reference
EnergaOutagesClient / EnergaOutagesClientSync
All async methods have identical sync equivalents on EnergaOutagesClientSync.
client = EnergaOutagesClient(
session=None, # optional aiohttp.ClientSession to reuse
cache_ttl_seconds=300, # how long to cache the shutdown list (default 5 min)
timeout_seconds=10, # HTTP request timeout
)
get_shutdowns(force=False) → list[Shutdown]
Returns all currently active shutdowns from the Energa API.
Uses the TTL cache unless force=True.
shutdowns = await client.get_shutdowns()
for s in shutdowns:
print(s.region_name, s.start_date, s.message)
check_location(lat, lon, margin_m=200, now=None, force=False) → Optional[OutageMatch]
Returns the highest-confidence match for the given GPS coordinates, or None if no active outage is nearby.
| Argument | Type | Description |
|---|---|---|
lat |
float | Latitude (WGS84, decimal degrees) |
lon |
float | Longitude (WGS84, decimal degrees) |
margin_m |
float | Distance in metres beyond polygon boundary still considered a match (default 200) |
now |
datetime | Override current time — useful for testing |
force |
bool | Bypass cache |
check_location_all(lat, lon, margin_m=200, ...) → list[OutageMatch]
Same as check_location but returns all matches sorted by confidence descending.
Useful when a location sits on the boundary between two outage polygons.
check_address(city, street=None, number=None, force=False) → list[AddressMatch]
Returns all shutdowns whose parsed message matches the given address, sorted by confidence descending.
| Argument | Type | Description |
|---|---|---|
city |
str | City or village name (required) |
street |
str | None | Street name. Prefixes like ul., al., os., gen. are stripped automatically |
number |
str | None | Building number. Matched exactly or against od X do Y ranges |
Prefix stripping means all of these are equivalent:
await client.check_address(city="Gdańsk", street="Dworska")
await client.check_address(city="Gdańsk", street="ul. Dworska")
await client.check_address(city="Gdańsk", street="ulica Dworska")
Return types
OutageMatch
Returned by check_location / check_location_all.
| Attribute | Type | Description |
|---|---|---|
confidence |
float | 0.0–1.0. 1.0 = inside polygon, linear decay to 0.0 at margin_m |
is_inside |
bool | True if the point is inside the outage polygon |
distance_to_boundary_m |
float | Metres to the nearest polygon edge. 0.0 if inside |
shutdown |
Shutdown |
Full shutdown details |
guid |
str | Shortcut to shutdown.guid |
to_dict() |
dict | Flat dict, suitable for Home Assistant extra_state_attributes |
AddressMatch
Returned by check_address.
| Attribute | Type | Description |
|---|---|---|
confidence |
float | 1.0 = all fields matched; 0.7 = street matched but number not confirmed |
matched_address |
ParsedAddress |
The specific address entry that matched |
shutdown |
Shutdown |
Full shutdown details |
to_dict() |
dict | Flat dict |
Shutdown
| Attribute | Type | Description |
|---|---|---|
guid |
str | Unique shutdown ID |
region_name |
str | Region, e.g. "Gdańsk" |
dept_name |
str | Department, e.g. "Gdańsk" |
areas |
list[str] | Administrative area names |
message |
str | Free-text affected addresses |
start_date |
datetime | Outage start (UTC) |
end_date |
datetime | Outage end (UTC) |
hours |
list[HourWindow] | Sub-windows within the day |
shutdown_type |
int | 1 = planned, 2 = emergency |
shutdown_type_label |
str | "planned" or "emergency" |
ring |
list[[lon, lat]] | GeoJSON polygon boundary |
centroid_lon/lat |
float | Polygon centre point |
parsed_addresses() |
list[ParsedAddress] | Parses message into structured addresses |
ParsedAddress
Structured result of parsing a shutdown message.
| Attribute | Type | Description |
|---|---|---|
place |
str | City or village name |
street |
str | None | Street name, None for rural addresses |
numbers |
list[str] | Building numbers, e.g. ["11", "13/A", "od 20 do 22"] |
str(addr) |
str | Human-readable, e.g. "Gdańsk ul. Dworska 11, 13/A" |
Confidence scoring
GPS-based (check_location)
Point inside polygon → confidence = 1.0
Point outside, within margin → confidence = 1.0 − (distance / margin_m)
Point beyond margin → no match returned
Address-based (check_address)
City + street + number all match (exact or within od/do range) → 1.0
City + street match, number provided but not found in list → 0.7
City + street match, no number asked → 1.0
City only match → 1.0
A confidence of 0.7 means the street segment is definitely affected, but your specific building number was not listed — it may still be impacted.
Home Assistant integration
EnergaOutagesClient is designed to be used in a Home Assistant custom integration:
- Async-first — drop into a
DataUpdateCoordinatorwith no threading concerns - Shared session — pass HA's
aiohttp_client.async_get_clientsession(hass)to avoid creating extra connections to_dict()— bothOutageMatchandAddressMatchreturn a flat dict ready forextra_state_attributesforce=True— for manual refresh triggered by a service call
from homeassistant.helpers.aiohttp_client import async_get_clientsession
from energa_outages_api import EnergaOutagesClient
session = async_get_clientsession(hass)
client = EnergaOutagesClient(session=session, cache_ttl_seconds=300)
# In coordinator _async_update_data:
match = await client.check_location(lat=hass.config.latitude, lon=hass.config.longitude)
Exceptions
| Exception | When raised |
|---|---|
EnergaOutagesError |
Base class for all library exceptions |
EnergaOutagesAPIError |
HTTP or network failure fetching outage data |
EnergaOutagesParseError |
Unexpected structure in the API response |
from energa_outages_api import EnergaOutagesAPIError, EnergaOutagesParseError
try:
match = await client.check_location(lat=54.352, lon=18.647)
except EnergaOutagesAPIError as e:
print(f"Could not reach Energa API: {e}")
except EnergaOutagesParseError as e:
print(f"Unexpected API response: {e}")
Coverage
Energa Operator serves northern and central Poland. Regions covered include Gdańsk, Gdynia, Sopot, Toruń, Bydgoszcz, Olsztyn, Płock, Włocławek, Kalisz, Konin, and surrounding areas. Wrocław and southern Poland are served by Tauron, not Energa — queries for those areas will return no results.
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file energa_outages_api-1.0.0.tar.gz.
File metadata
- Download URL: energa_outages_api-1.0.0.tar.gz
- Upload date:
- Size: 19.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b68cb8fd41bb07f628432d566bb9de6db1ba51e612b9f4d6c1336f8f8f1ff010
|
|
| MD5 |
1b2d5be2f7b1be41814d1a077348426a
|
|
| BLAKE2b-256 |
7137d3dbf24613d046b1f9bb75367a47e0850212d60718b5ad8e7ff9a27f27dd
|
Provenance
The following attestation bundles were made for energa_outages_api-1.0.0.tar.gz:
Publisher:
publish.yml on vincentto13/energa-outages-api
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
energa_outages_api-1.0.0.tar.gz -
Subject digest:
b68cb8fd41bb07f628432d566bb9de6db1ba51e612b9f4d6c1336f8f8f1ff010 - Sigstore transparency entry: 1292716459
- Sigstore integration time:
-
Permalink:
vincentto13/energa-outages-api@8b39f18cf1e0acb00ab0593c720987ecbb25249e -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/vincentto13
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@8b39f18cf1e0acb00ab0593c720987ecbb25249e -
Trigger Event:
push
-
Statement type:
File details
Details for the file energa_outages_api-1.0.0-py3-none-any.whl.
File metadata
- Download URL: energa_outages_api-1.0.0-py3-none-any.whl
- Upload date:
- Size: 16.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1167f6f876c0f02346ba8fe517ac571850088e6ac6b68ffc7d3a33e76bf65c21
|
|
| MD5 |
de279ba3b59039bf4d0c32674ff0074b
|
|
| BLAKE2b-256 |
b71b4b355c4f2a4d6e7769afd3053ffc0c4d901b6b5250b8e386fd2adbc4c3af
|
Provenance
The following attestation bundles were made for energa_outages_api-1.0.0-py3-none-any.whl:
Publisher:
publish.yml on vincentto13/energa-outages-api
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
energa_outages_api-1.0.0-py3-none-any.whl -
Subject digest:
1167f6f876c0f02346ba8fe517ac571850088e6ac6b68ffc7d3a33e76bf65c21 - Sigstore transparency entry: 1292716538
- Sigstore integration time:
-
Permalink:
vincentto13/energa-outages-api@8b39f18cf1e0acb00ab0593c720987ecbb25249e -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/vincentto13
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@8b39f18cf1e0acb00ab0593c720987ecbb25249e -
Trigger Event:
push
-
Statement type: