Add Home Assistant Stelloauth app #1
@@ -0,0 +1,6 @@
|
|||||||
|
.venv/
|
||||||
|
.pytest_cache/
|
||||||
|
__pycache__/
|
||||||
|
*.pyc
|
||||||
|
.coverage
|
||||||
|
artifacts/
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
[pytest]
|
||||||
|
markers =
|
||||||
|
upstream: fetches and validates pinned upstream source
|
||||||
|
docker: builds or runs the add-on image
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
name: Stelloauth for Home Assistant
|
||||||
|
url: https://git.radixadm.dk/dennis/homeassistant-stelloauth-addon.git
|
||||||
|
maintainer: Dennis / Radix ApS
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
pytest==8.4.2
|
||||||
|
PyYAML==6.0.2
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
name: Stelloauth
|
||||||
|
version: "0.1.0"
|
||||||
|
slug: stelloauth
|
||||||
|
description: Local OAuth worker for Stellantis Vehicles using CloakBrowser
|
||||||
|
url: https://git.radixadm.dk/dennis/homeassistant-stelloauth-addon
|
||||||
|
arch:
|
||||||
|
- amd64
|
||||||
|
- aarch64
|
||||||
|
startup: application
|
||||||
|
boot: auto
|
||||||
|
init: true
|
||||||
|
watchdog: http://[HOST]:[PORT:8080]/
|
||||||
|
ports:
|
||||||
|
8080/tcp: null
|
||||||
|
ports_description:
|
||||||
|
8080/tcp: Temporary LAN access for troubleshooting only
|
||||||
|
options:
|
||||||
|
queue_timeout: 60s
|
||||||
|
rate_limit_count: 5
|
||||||
|
rate_limit_duration: 1h
|
||||||
|
schema:
|
||||||
|
queue_timeout: match(^[1-9][0-9]*(ms|s|m|h)$)
|
||||||
|
rate_limit_count: int(1,20)
|
||||||
|
rate_limit_duration: match(^[1-9][0-9]*(ms|s|m|h)$)
|
||||||
@@ -0,0 +1,10 @@
|
|||||||
|
configuration:
|
||||||
|
queue_timeout:
|
||||||
|
name: Køventetid
|
||||||
|
description: Angiver hvor længe et loginforsøg må vente i køen.
|
||||||
|
rate_limit_count:
|
||||||
|
name: Loginforsøg
|
||||||
|
description: Angiver det maksimale antal loginforsøg i hver periode.
|
||||||
|
rate_limit_duration:
|
||||||
|
name: Rate limit-periode
|
||||||
|
description: Angiver periodens længde for begrænsning af loginforsøg.
|
||||||
@@ -0,0 +1,10 @@
|
|||||||
|
configuration:
|
||||||
|
queue_timeout:
|
||||||
|
name: Queue timeout
|
||||||
|
description: Sets how long a login attempt may wait in the queue.
|
||||||
|
rate_limit_count:
|
||||||
|
name: Login attempts
|
||||||
|
description: Sets the maximum number of login attempts in each period.
|
||||||
|
rate_limit_duration:
|
||||||
|
name: Rate limit period
|
||||||
|
description: Sets the length of the login attempt rate limit period.
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
from __future__ import annotations
|
||||||
|
import hashlib
|
||||||
|
from pathlib import Path
|
||||||
|
import yaml
|
||||||
|
|
||||||
|
ROOT = Path(__file__).parents[1]
|
||||||
|
REPOSITORY_URL = "https://git.radixadm.dk/dennis/homeassistant-stelloauth-addon.git"
|
||||||
|
|
||||||
|
def load_yaml(path: str) -> dict:
|
||||||
|
with (ROOT / path).open(encoding="utf-8") as handle:
|
||||||
|
value = yaml.safe_load(handle)
|
||||||
|
assert isinstance(value, dict)
|
||||||
|
return value
|
||||||
|
|
||||||
|
def test_repository_metadata() -> None:
|
||||||
|
metadata = load_yaml("repository.yaml")
|
||||||
|
assert metadata["url"] == REPOSITORY_URL
|
||||||
|
assert metadata["name"] == "Stelloauth for Home Assistant"
|
||||||
|
assert metadata["maintainer"] == "Dennis / Radix ApS"
|
||||||
|
|
||||||
|
def test_addon_contract() -> None:
|
||||||
|
config = load_yaml("stelloauth/config.yaml")
|
||||||
|
assert config["slug"] == "stelloauth"
|
||||||
|
assert config["version"] == "0.1.0"
|
||||||
|
assert config["arch"] == ["amd64", "aarch64"]
|
||||||
|
assert config["startup"] == "application"
|
||||||
|
assert config["boot"] == "auto"
|
||||||
|
assert config["init"] is True
|
||||||
|
assert config["watchdog"] == "http://[HOST]:[PORT:8080]/"
|
||||||
|
assert config["ports"] == {"8080/tcp": None}
|
||||||
|
for key in ("ingress", "host_network", "privileged", "full_access", "docker_api", "devices", "map"):
|
||||||
|
assert key not in config
|
||||||
|
|
||||||
|
def test_defaults_and_schema_are_aligned() -> None:
|
||||||
|
config = load_yaml("stelloauth/config.yaml")
|
||||||
|
assert config["options"] == {
|
||||||
|
"queue_timeout": "60s",
|
||||||
|
"rate_limit_count": 5,
|
||||||
|
"rate_limit_duration": "1h",
|
||||||
|
}
|
||||||
|
assert set(config["schema"]) == set(config["options"])
|
||||||
|
assert config["schema"]["rate_limit_count"] == "int(1,20)"
|
||||||
|
|
||||||
|
def test_repository_hostname_derivation() -> None:
|
||||||
|
repository_id = hashlib.sha1(REPOSITORY_URL.lower().encode()).hexdigest()[:8]
|
||||||
|
assert repository_id == "0031621f"
|
||||||
|
assert f"{repository_id}-stelloauth" == "0031621f-stelloauth"
|
||||||
|
|
||||||
|
def test_translations_cover_every_option() -> None:
|
||||||
|
keys = set(load_yaml("stelloauth/config.yaml")["options"])
|
||||||
|
for language in ("da", "en"):
|
||||||
|
translation = load_yaml(f"stelloauth/translations/{language}.yaml")
|
||||||
|
assert set(translation["configuration"]) == keys
|
||||||
|
for entry in translation["configuration"].values():
|
||||||
|
assert set(entry) == {"name", "description"}
|
||||||
|
assert all(isinstance(value, str) and value.strip() for value in entry.values())
|
||||||
Reference in New Issue
Block a user