58 lines
1.6 KiB
Python
58 lines
1.6 KiB
Python
from dataclasses import dataclass
|
|
from typing import TypeVar, ParamSpec, Callable
|
|
from functools import wraps
|
|
|
|
P = ParamSpec("P")
|
|
T = TypeVar("T")
|
|
def after(func: Callable[[], None]) -> Callable[P, T]:
|
|
"""Runs @func after the decorated function exits."""
|
|
def decorator(f: Callable[P, T]) -> Callable[P, T]:
|
|
def inner(*args: P.args, **kwargs: P.kwargs) -> T:
|
|
ret = f(*args, **kwargs)
|
|
func()
|
|
return ret
|
|
return inner
|
|
return decorator
|
|
|
|
@dataclass
|
|
class KodiTime:
|
|
hours: int
|
|
minutes: int
|
|
seconds: int
|
|
|
|
def to_seconds(self) -> int:
|
|
return self.hours * 3600 + self.minutes * 59 + self.seconds
|
|
|
|
def seconds_to_kodi_format(seconds: int) -> KodiTime:
|
|
"""Convert seconds into hours, minutes, and seconds as Kodi wants that."""
|
|
hours = seconds // 3600
|
|
seconds -= hours * 3600
|
|
minutes = seconds // 60
|
|
seconds -= minutes * 60
|
|
return KodiTime(
|
|
hours=hours,
|
|
minutes=minutes,
|
|
seconds=seconds,
|
|
)
|
|
|
|
|
|
def find(l: list[T], pred: Callable[[T], bool]) -> T | None:
|
|
for i in l:
|
|
if pred(i):
|
|
return i
|
|
return None
|
|
|
|
def recursive_dict_merge(base: dict, update: dict) -> dict:
|
|
unique_keys = set([*base.keys(), *update.keys()])
|
|
out = {}
|
|
for key in unique_keys:
|
|
if key in base and key not in update:
|
|
out[key] = base[key]
|
|
elif key not in base and key in update:
|
|
out[key] = update[key]
|
|
else:
|
|
if not isinstance(update[key], dict):
|
|
out[key] = update[key]
|
|
else:
|
|
out[key] = recursive_dict_merge(base[key], update[key])
|
|
return out |