Исходный код soniks_client.models

"""Описание задания наблюдения, полученного от портала."""

from dataclasses import dataclass
from datetime import UTC, datetime

from core.types import TLE


[документация] @dataclass class JobData: """Задание наблюдения, полученное от портала.""" id: str start: datetime end: datetime tle: TLE frequency: int mode: str baud: int norad_cat_id: int | None = None
[документация] @classmethod def from_dict(cls, job_data: dict[str, str | int | None]) -> "JobData": """Собрать задание из ответа API. Args: job_data: Словарь одного задания из ответа портала. Returns: Разобранное задание наблюдения. """ start = cls.parse_datetime(job_data["start"]) end = cls.parse_datetime(job_data["end"]) baud = job_data["baud"] or 0 tle = { "tle0": job_data.get("tle0", ""), "tle1": job_data.get("tle1", ""), "tle2": job_data.get("tle2", ""), } return cls( id=str(job_data["id"]), start=start, end=end, tle=tle, frequency=job_data["frequency"], mode=job_data["mode"], baud=baud, norad_cat_id=job_data.get("norad_cat_id"), )
[документация] @staticmethod def parse_datetime(datetime_str: str) -> datetime: """Разобрать метку времени из ответа портала в ``datetime`` с UTC.""" parsed = datetime.fromisoformat(datetime_str) # Портал шлёт UTC; строка без смещения — форма записи, а не локальное # время. Наивное значение роняло сверку расписания (сравнение с # datetime.now(tz=UTC) в sync.py) и трактовалось APScheduler по зоне # процесса, то есть проход планировался не на то время. if parsed.tzinfo is None: return parsed.replace(tzinfo=UTC) return parsed.astimezone(UTC)
def __repr__(self) -> str: start_str = self.start.strftime("%d-%m-%Y %H:%M (UTC)") end_str = self.end.strftime("%d-%m-%Y %H:%M (UTC)") tle0 = self.tle["tle0"] satellite_name = tle0.removeprefix("0 ") return ( f"JobData(id={self.id}, start={start_str}, end={end_str}, " f"satellite_name={satellite_name}, frequency={self.frequency}, " f"mode={self.mode}, baud={self.baud}, " f"norad_cat_id={self.norad_cat_id})" )