| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114 |
- """
- Модуль предоставляет тип результата.
- """
- from typing import TypeVar
- T = TypeVar("T")
- class Result[T]:
- """
- Класс результата. Предоставляет полезный результат, либо ошибку.
- Если экземпляр содержит ошибку и не было её получения (либо проверки)
- приложение аварийно завершится.
- """
- __slots__: list[str] = ["__val", "__err", "__is_check"]
- def __init__(self, result: T | None = None, err: str | None = None) -> None:
- # Инициализируем __is_check до любых возможных exit()
- self.__is_check = False
- """Признак предварительной проверки ошибки"""
- # Результат и ошибка не могут быть вместе None
- if result is None and err is None:
- print("=" * 80)
- print("ERROR: Result.__init__(): called with both result=None and err=None")
- print("This indicates a programming error in the code.")
- print("=" * 80)
- exit(1)
- # Результат есть. err не может быть значением
- if result is not None and err is not None:
- msg = "Result.__init__(): some and err not None."
- self.__out(msg)
- exit(2)
- self.__val: T | None = result
- """Содержит результат"""
- self.__err: str | None = err
- """Содержит ошибку"""
- @property
- def is_err(self) -> bool:
- """
- Возвращает признак содержания ошибки.
- """
- _is_err = self.__err is not None
- self.__is_check = True
- return _is_err
- def hassert(self, msg: str) -> None:
- """
- Принудительная проверка на отсутствие ошибки/ Если ошибка -- падение.
- """
- _is_err = self.__err is not None
- self.__is_check = True
- if _is_err:
- print("=" * 80)
- print("ERROR: Missing required environment variable!")
- print("=" * 80)
- print(f"Context: {msg}")
- if self.__err:
- print(f"Error details: {self.__err}")
- print("=" * 80)
- self.__out(msg)
- exit(4)
- @property
- def val(self) -> T:
- """Возвращает хранимый результат"""
- if not self.__is_check:
- msg = "Result.val(): result not checked."
- self.__out(msg)
- exit(3)
- if self.__val is None:
- msg = "Result.val(): err not None."
- self.__out(msg)
- exit(4)
- return self.__val
- @property
- def err(self) -> str:
- """Возвращает ошибку из результата"""
- if self.__err is None:
- msg = "Result.err(): error is None."
- self.__out(msg)
- exit(5)
- return self.__err
- def __del__(self) -> None:
- """Контроль на проверенную ошибку"""
- # Проверяем наличие атрибута на случай неполной инициализации
- if not hasattr(self, "_Result__is_check"):
- return
- if self.__is_check:
- return
- msg = "Result.__del__(): error not checked"
- self.__out(msg)
- exit(6)
- def __out(self, msg: str) -> None:
- """Выводит детальную информацию об ошибке"""
- print(f"Result error details:")
- print(f" Message: {msg}")
- if self.__err:
- # Извлекаем имя переменной из сообщения об ошибке, если возможно
- err_msg = self.__err
- if "env " in err_msg and " not set" in err_msg:
- # Формат: "env_str(): env VAR_NAME not set"
- try:
- var_name = err_msg.split("env ")[1].split(" not set")[0]
- print(f" Missing environment variable: {var_name}")
- except IndexError:
- pass
- print(f" Error: {err_msg}")
- print(f" Result value: {self.__val}")
|