diff --git a/.gitignore b/.gitignore index e2f8e49..d00e33a 100644 --- a/.gitignore +++ b/.gitignore @@ -6,4 +6,4 @@ __pycache__ *.log .idea/ *.idea -/app/config/config.yml +/app/config/config.ini diff --git a/app/config/config-template.yml b/app/backups/.keep similarity index 100% rename from app/config/config-template.yml rename to app/backups/.keep diff --git a/app/config/.env-template b/app/config/.env-template index e69de29..da2f9b3 100644 --- a/app/config/.env-template +++ b/app/config/.env-template @@ -0,0 +1,2 @@ +TG_CHAT_ID = +TG_BOT_TOKEN = \ No newline at end of file diff --git a/app/config/__init__.py b/app/config/__init__.py index e69de29..e46829c 100644 --- a/app/config/__init__.py +++ b/app/config/__init__.py @@ -0,0 +1,5 @@ +from .config import config + +__all__ = [ + "config", +] diff --git a/app/config/config-template.ini b/app/config/config-template.ini new file mode 100644 index 0000000..52735fe --- /dev/null +++ b/app/config/config-template.ini @@ -0,0 +1,19 @@ +# Конфиг для отправки оповещений через телеграм +[tg] +send: False + +# Конфиг удалённого гит репозитория +[git] +push: False +user: +mail: +pwd: +dir: +remote: +token: + +[log] +console_lvl: 20 +file_lvl: 30 +date_format: %Y-%m-%d %H:%M:%S +format= [%(asctime)s.%(msecs)03d] %(module)-25s:%(lineno)4d | %(funcName)-20s| %(levelname)-8s | %(message)s \ No newline at end of file diff --git a/app/config/config.py b/app/config/config.py new file mode 100644 index 0000000..178de16 --- /dev/null +++ b/app/config/config.py @@ -0,0 +1,95 @@ +from dataclasses import dataclass, field +from typing import Optional +import logging + +import configparser +import os + + +from dotenv import load_dotenv + + +def default_logging(main_logging: logging) -> None: + log_dir: str = os.path.join( + os.path.dirname(os.path.abspath(os.path.dirname(__file__))), "logs" + ) + main_logging.basicConfig( + level=20, + datefmt="%Y-%m-%d %H:%M:%S", + format="[%(asctime)s.%(msecs)03d] %(module)-25s:%(lineno)4d | %(funcName)-20s| %(levelname)-8s | %(message)s", + ) + file_handler = main_logging.FileHandler(os.path.join(log_dir, "logfile.log")) + file_handler.setLevel(30) + file_handler.setFormatter( + logging.Formatter( + "[%(asctime)s.%(msecs)03d] %(module)s:%(lineno)4d | %(funcName)s| %(levelname)s | %(message)s" + ) + ) + main_logging.getLogger().addHandler(file_handler) + main_logging.info("success configure logging") + + +default_logging(logging) + + +def configure_loging(main_logging: logging) -> None: + log_dir: str = os.path.join( + os.path.dirname(os.path.abspath(os.path.dirname(__file__))), "logs" + ) + logging.info("configure logging") + main_logging.basicConfig( + level=cfg.log.console_lvl, + datefmt=cfg.log.dare_format, + format=cfg.log.format, + ) + handler = main_logging.FileHandler(os.path.join(log_dir, "logfile.log")) + handler.setLevel(cfg.log.file_lvl) + handler.setFormatter(logging.Formatter(cfg.log.format)) + logging.getLogger().addHandler(handler) + logging.info("success configure logging") + + +def load_config(): + cfg_dir: str = os.path.abspath(os.path.dirname(__file__)) + logging.info("loading env") + load_dotenv(dotenv_path=os.path.join(cfg_dir, ".env")) + logging.info("success loading env") + + logging.info("loading config") + loaded_config: configparser.ConfigParser = configparser.ConfigParser( + interpolation=None + ) + user_config: str = os.path.join(cfg_dir, "config.ini") + loaded_config.read(user_config) + logging.info("success loading config") + return loaded_config + + +config = load_config() + + +@dataclass +class ConfigLog: + console_lvl: int = config["log"].getint("console_lvl") + file_lvl: int = config["log"].getint("file_lvl") + dare_format: str = config["log"].get("dare_format") + format: str = config["log"].get("format") + + +@dataclass +class ConfigTelegram: + send: bool = config["tg"].getboolean("send") + if send: + bot_token: str = os.getenv("TG_BOT_TOKEN") + chat_id: int = int(os.getenv("TG_CHAT_ID")) + + +@dataclass() +class ConfigAll: + log: ConfigLog = ConfigLog + tg: ConfigTelegram = ConfigTelegram + + +cfg = ConfigAll + +configure_loging(logging) diff --git a/app/main.py b/app/main.py index cd9ac48..8015bdc 100644 --- a/app/main.py +++ b/app/main.py @@ -1,6 +1,15 @@ +from config import config as cfg +import logging as log + + def main(): pass if __name__ == "__main__": - main() + log.info("Starting app") + try: + main() + except KeyboardInterrupt: + log.info("Manual app stopped") + log.info("App stopped") diff --git a/pyproject.toml b/pyproject.toml index 8b9a83e..b1c53f1 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,4 +4,6 @@ version = "0.1.0" description = "Create backup network devices" readme = "README.md" requires-python = ">=3.13" -dependencies = [] +dependencies = [ + "python-dotenv>=1.1.0", +] diff --git a/uv.lock b/uv.lock index a85df5e..94136d2 100644 --- a/uv.lock +++ b/uv.lock @@ -6,3 +6,18 @@ requires-python = ">=3.13" name = "net-backup" version = "0.1.0" source = { virtual = "." } +dependencies = [ + { name = "python-dotenv" }, +] + +[package.metadata] +requires-dist = [{ name = "python-dotenv", specifier = ">=1.1.0" }] + +[[package]] +name = "python-dotenv" +version = "1.1.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/88/2c/7bb1416c5620485aa793f2de31d3df393d3686aa8a8506d11e10e13c5baf/python_dotenv-1.1.0.tar.gz", hash = "sha256:41f90bc6f5f177fb41f53e87666db362025010eb28f60a01c9143bfa33a2b2d5", size = 39920, upload-time = "2025-03-25T10:14:56.835Z" } +wheels = [ + { url = "https://files.pythonhosted.org/packages/1e/18/98a99ad95133c6a6e2005fe89faedf294a748bd5dc803008059409ac9b1e/python_dotenv-1.1.0-py3-none-any.whl", hash = "sha256:d7c01d9e2293916c18baf562d95698754b0dbbb5e74d457c45d4f6561fb9d55d", size = 20256, upload-time = "2025-03-25T10:14:55.034Z" }, +]