Compare commits
23 Commits
v1.0.3-rc1
...
d20b48e6b1
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
d20b48e6b1 | ||
|
|
d1438f9a0b | ||
|
|
c1b7b16251 | ||
|
|
e6c2644ea5 | ||
|
|
fc5f6e7c93 | ||
|
|
fa052cdfc9 | ||
|
|
f6f799e85f | ||
|
|
a44308a4e1 | ||
|
|
dd5bb2916b | ||
|
|
67bb1e49ef | ||
|
|
aaea39657e | ||
|
|
81c19b552d | ||
|
|
0d609ade9a | ||
|
|
2b453f4b5e | ||
|
|
62904f4c09 | ||
|
|
35d5232d8e | ||
|
|
1c3b0ae0b5 | ||
|
|
d2e8f77725 | ||
|
|
92e99e03ef | ||
|
|
903a512f99 | ||
|
|
f385ee3a5a | ||
|
|
573f91e2f9 | ||
|
|
025a6475dd |
24
README.md
24
README.md
@@ -2,7 +2,8 @@
|
|||||||
|
|
||||||
## Adding to your dashboard
|
## Adding to your dashboard
|
||||||
|
|
||||||
You can add an overview of the current infection numbers to your dashboard using the [multiple-entity-row](https://github.com/benct/lovelace-multiple-entity-row) card:
|
You can add an overview of the current infection and vaccination numbers to your dashboard
|
||||||
|
using the [multiple-entity-row](https://github.com/benct/lovelace-multiple-entity-row) card:
|
||||||
|
|
||||||
```yaml
|
```yaml
|
||||||
type: entities
|
type: entities
|
||||||
@@ -24,4 +25,25 @@ entities:
|
|||||||
secondary_info:
|
secondary_info:
|
||||||
attribute: incidence
|
attribute: incidence
|
||||||
unit: cases/100k
|
unit: cases/100k
|
||||||
|
- type: custom:multiple-entity-row
|
||||||
|
entity: sensor.covid_19_vaccinations_augsburg
|
||||||
|
entities:
|
||||||
|
- attribute: ratio_vaccinated_once
|
||||||
|
name: Once
|
||||||
|
format: precision1
|
||||||
|
unit: '%'
|
||||||
|
- attribute: ratio_vaccinated_full
|
||||||
|
name: Fully
|
||||||
|
format: precision1
|
||||||
|
unit: '%'
|
||||||
|
- attribute: ratio_vaccinated_total
|
||||||
|
name: Total
|
||||||
|
format: precision1
|
||||||
|
unit: '%'
|
||||||
|
show_state: false
|
||||||
|
icon: mdi:needle
|
||||||
|
name: COVID-19 Vaccinations
|
||||||
|
secondary_info:
|
||||||
|
attribute: date
|
||||||
|
format: date
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -12,11 +12,11 @@ if TYPE_CHECKING:
|
|||||||
from homeassistant.core import HomeAssistant
|
from homeassistant.core import HomeAssistant
|
||||||
|
|
||||||
from .const import DOMAIN
|
from .const import DOMAIN
|
||||||
from .crawler import CovidCrawler, IncidenceData
|
from .crawler import CovidCrawler
|
||||||
|
|
||||||
_LOGGER = logging.getLogger(__name__)
|
_LOGGER = logging.getLogger(__name__)
|
||||||
|
|
||||||
__version__ = "0.1.0"
|
__version__ = "1.2.2"
|
||||||
|
|
||||||
PLATFORMS = ["sensor"]
|
PLATFORMS = ["sensor"]
|
||||||
|
|
||||||
|
|||||||
@@ -59,9 +59,12 @@ class VaccinationData:
|
|||||||
total_vaccinations: int = 0
|
total_vaccinations: int = 0
|
||||||
num_vaccinated_once: int = 0
|
num_vaccinated_once: int = 0
|
||||||
num_vaccinated_full: int = 0
|
num_vaccinated_full: int = 0
|
||||||
|
num_vaccinated_booster: int = 0
|
||||||
|
|
||||||
ratio_vaccinated_once: float = 0.0
|
ratio_vaccinated_once: float = 0.0
|
||||||
ratio_vaccinated_full: float = 0.0
|
ratio_vaccinated_full: float = 0.0
|
||||||
|
ratio_vaccinated_total: float = 0.0
|
||||||
|
ratio_vaccinated_booster: float = 0.0
|
||||||
|
|
||||||
|
|
||||||
class CovidCrawlerBase(ABC):
|
class CovidCrawlerBase(ABC):
|
||||||
@@ -106,11 +109,11 @@ class CovidCrawler(CovidCrawlerBase):
|
|||||||
)
|
)
|
||||||
soup = await self._fetch(url)
|
soup = await self._fetch(url)
|
||||||
|
|
||||||
match = soup.find(class_="frame--type-textpic")
|
match = soup.find(id="c1075340")
|
||||||
text = match.p.text
|
text = match.text.strip()
|
||||||
_log.debug(f"Infection data text: {text}")
|
_log.debug(f"Infection data text: {text}")
|
||||||
|
|
||||||
matches = re.search(r"(\d+,\d+)\sNeuinfektion", text)
|
matches = re.search(r"(\d+(,\d+)?)\sNeuinfektion", text)
|
||||||
if not matches:
|
if not matches:
|
||||||
raise ValueError(
|
raise ValueError(
|
||||||
f"Could not extract incidence from scraped web page, {text=}"
|
f"Could not extract incidence from scraped web page, {text=}"
|
||||||
@@ -119,18 +122,15 @@ class CovidCrawler(CovidCrawlerBase):
|
|||||||
incidence = parse_num(matches.group(1), t=float)
|
incidence = parse_num(matches.group(1), t=float)
|
||||||
_log.debug(f"Parsed incidence: {incidence}")
|
_log.debug(f"Parsed incidence: {incidence}")
|
||||||
|
|
||||||
text = match.h2.text
|
match = soup.find(id="c1052517")
|
||||||
matches = re.search(r"\((\d+)\. (\w+).*\)", text)
|
text = match.text.strip()
|
||||||
|
matches = re.search(r"Stand: (\d+)\. (\w+) (\d{4})", text)
|
||||||
if not matches:
|
if not matches:
|
||||||
raise ValueError(f"Could not extract date from scraped web page, {text=}")
|
raise ValueError(f"Could not extract date from scraped web page, {text=}")
|
||||||
|
|
||||||
date = parse_date(matches.group(1), matches.group(2))
|
date = parse_date(matches.group(1), matches.group(2), matches.group(3))
|
||||||
_log.debug(f"Parsed date: {date}")
|
_log.debug(f"Parsed date: {date}")
|
||||||
|
|
||||||
match = match.find_next_sibling(class_="frame--type-textpic")
|
|
||||||
text = match.text
|
|
||||||
_log.debug(f"Infection counts text: {text}")
|
|
||||||
|
|
||||||
regexes = [
|
regexes = [
|
||||||
r"Insgesamt: (?P<total_cases>[0-9.]+)",
|
r"Insgesamt: (?P<total_cases>[0-9.]+)",
|
||||||
r"genesen: (?P<num_recovered>[0-9.]+)",
|
r"genesen: (?P<num_recovered>[0-9.]+)",
|
||||||
@@ -167,9 +167,9 @@ class CovidCrawler(CovidCrawlerBase):
|
|||||||
result = soup.find(id=container_id)
|
result = soup.find(id=container_id)
|
||||||
text = re.sub(r"\s+", " ", result.text)
|
text = re.sub(r"\s+", " ", result.text)
|
||||||
regexes = [
|
regexes = [
|
||||||
r"(?P<total_vaccinations>\d+[.]\d+) Impfdosen",
|
r"(?P<total_vaccinations>\d+([.]\d+)?) Personen in Augsburg",
|
||||||
r"Weitere (?P<num_vaccinated_once>\d+[.]\d+) Personen haben die Erstimpfung erhalten",
|
r"(?P<num_vaccinated_full>\d+([.]\d+)?) Personen in Augsburg",
|
||||||
r"(?P<num_vaccinated_full>\d+[.]\d+) Personen sind bereits vollständig geimpft",
|
r"(?P<num_vaccinated_booster>\d+([.]\d+)?) Personen, also",
|
||||||
]
|
]
|
||||||
values = {}
|
values = {}
|
||||||
for r in regexes:
|
for r in regexes:
|
||||||
@@ -187,15 +187,24 @@ class CovidCrawler(CovidCrawlerBase):
|
|||||||
if not matches:
|
if not matches:
|
||||||
raise ValueError(f"Could not extract date from scraped web page, {text=}")
|
raise ValueError(f"Could not extract date from scraped web page, {text=}")
|
||||||
|
|
||||||
|
values["num_vaccinated_once"] = (
|
||||||
|
values["total_vaccinations"] - values["num_vaccinated_full"]
|
||||||
|
)
|
||||||
|
|
||||||
values["date"] = parse_date(**matches.groupdict()).strftime("%Y-%m-%d")
|
values["date"] = parse_date(**matches.groupdict()).strftime("%Y-%m-%d")
|
||||||
result = VaccinationData(**values)
|
result = VaccinationData(**values)
|
||||||
|
|
||||||
# Total population in Augsburg as of 2020
|
# Total population in Augsburg as listed on the crawled page
|
||||||
# https://www.augsburg.de/fileadmin/user_upload/buergerservice_rathaus/rathaus/statisiken_und_geodaten/statistiken/Monitoring/Demografiemonitoring_der_Stadt_Augsburg_2021.pdf
|
population = 298014
|
||||||
population = 299021
|
|
||||||
|
|
||||||
result.ratio_vaccinated_full = result.num_vaccinated_full / population
|
result.ratio_vaccinated_full = result.num_vaccinated_full / population * 100
|
||||||
result.ratio_vaccinated_once = result.num_vaccinated_once / population
|
result.ratio_vaccinated_once = result.num_vaccinated_once / population * 100
|
||||||
|
result.ratio_vaccinated_total = (
|
||||||
|
result.ratio_vaccinated_once + result.ratio_vaccinated_full
|
||||||
|
)
|
||||||
|
result.ratio_vaccinated_booster = (
|
||||||
|
result.num_vaccinated_booster / population * 100
|
||||||
|
)
|
||||||
_log.debug(f"Result data: {result}")
|
_log.debug(f"Result data: {result}")
|
||||||
|
|
||||||
return result
|
return result
|
||||||
|
|||||||
@@ -1,11 +1,15 @@
|
|||||||
{
|
{
|
||||||
"domain": "covid19_augsburg",
|
"domain": "covid19_augsburg",
|
||||||
"name": "COVID-19 Augsburg",
|
"name": "COVID-19 Augsburg",
|
||||||
"version": "0.1.0",
|
"version": "1.2.2",
|
||||||
"config_flow": true,
|
"config_flow": true,
|
||||||
"documentation": "https://github.com/AdrianoKF/home-assistant-covid19-augsburg",
|
"documentation": "https://github.com/AdrianoKF/home-assistant-covid19-augsburg",
|
||||||
"issue_tracker": "https://github.com/AdrianoKF/home-assistant-covid19-augsburg/issues",
|
"issue_tracker": "https://github.com/AdrianoKF/home-assistant-covid19-augsburg/issues",
|
||||||
"requirements": ["beautifulsoup4==4.8.2"],
|
"requirements": [
|
||||||
|
"beautifulsoup4==4.8.2"
|
||||||
|
],
|
||||||
"dependencies": [],
|
"dependencies": [],
|
||||||
"codeowners": ["@AdrianoKF"]
|
"codeowners": [
|
||||||
|
"@AdrianoKF"
|
||||||
|
]
|
||||||
}
|
}
|
||||||
@@ -9,7 +9,12 @@ async def async_setup_entry(hass, _, async_add_entities):
|
|||||||
"""Defer sensor setup to the shared sensor module."""
|
"""Defer sensor setup to the shared sensor module."""
|
||||||
coordinator = await get_coordinator(hass)
|
coordinator = await get_coordinator(hass)
|
||||||
|
|
||||||
async_add_entities([CoronaAugsburgSensor(coordinator)])
|
async_add_entities(
|
||||||
|
[
|
||||||
|
CoronaAugsburgSensor(coordinator),
|
||||||
|
CoronaAugsburgVaccinationSensor(coordinator),
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class CoronaAugsburgSensor(Entity):
|
class CoronaAugsburgSensor(Entity):
|
||||||
@@ -82,7 +87,7 @@ class CoronaAugsburgVaccinationSensor(Entity):
|
|||||||
|
|
||||||
@property
|
@property
|
||||||
def icon(self):
|
def icon(self):
|
||||||
return "mdi:biohazard"
|
return "mdi:needle"
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def unit_of_measurement(self):
|
def unit_of_measurement(self):
|
||||||
|
|||||||
1021
poetry.lock
generated
1021
poetry.lock
generated
File diff suppressed because it is too large
Load Diff
@@ -1,6 +1,6 @@
|
|||||||
[tool.poetry]
|
[tool.poetry]
|
||||||
name = "git add re"
|
name = "home_assistant_covid19_augsburg"
|
||||||
version = "0.1.0"
|
version = "1.2.2"
|
||||||
description = ""
|
description = ""
|
||||||
authors = ["Adrian Rumpold <a.rumpold@gmail.com>"]
|
authors = ["Adrian Rumpold <a.rumpold@gmail.com>"]
|
||||||
packages = [
|
packages = [
|
||||||
|
|||||||
Reference in New Issue
Block a user