import sys
import py_module.docker as docker
import json
import tarfile
import os

from .base import Base
from .docker_installer import Docker_installer

class Export_log(Base):

    def preload(self):
        self.logger.info('Проверяю наличие Docker-среды');
        with Docker_installer() as run:
            pass
        self.dockercli = docker.from_env();

    def postload(self):
        self.export_logs();

    def export_logs(self):
        self.export_docker(["containers", "images", "volumes", "nodes", "networks", "services"]);
        self.export_container_logs();
        self.form.msgbox(f'Логи для техподдержки собраны.\nПуть хранения логов: {sys.path[0]}/support_logs/');

    def export_docker(self, docker_objects: list = []):
        self.logger.info('Собираю информацию о docker-среде (containers, images, volumes, nodes, networks, services)')
        for docker_object in docker_objects:
            try:
                self.logger.debug(f'Открываю файл {sys.path[0]}/support_logs/{docker_object} для записи логов');
                with open(f'{sys.path[0]}/support_logs/{docker_object}.json', 'w') as file:
                    self.logger.info(f'Запрашиваю в Docker API список {docker_object}');
                    exporter = getattr(self.dockercli, docker_object).list();
                    self.logger.info(f'Сохраняю в файл {sys.path[0]}/support_logs/{docker_object}.json');
                    json.dump(exporter, file, indent = 4, default=lambda obj: obj.__dict__ if hasattr(obj, '__dict__') else None);
                    self.logger.debug(f'Сохранен dump {docker_object} в {sys.path[0]}/support_logs/{docker_object}.json');
            except:
                self.logger.error(f'Произошла ошибка при выгрузке информации о {docker_object} в docker-среде');
                continue

    def export_container_logs(self):
        self.logger.info('Начинаю сбор логов из контейнеров');
        try:
            self.logger.debug(f'Запрашиваю список контейнеров в Docker API');
            containers = self.dockercli.containers.list();
            self.logger.info(f'Список контейнеров:{[container.name+" ["+container.short_id+"]" for container in containers]}')
            for container in containers:
                self.logger.debug(f'Открываю файл {sys.path[0]}/support_logs/{container.name}.{container.short_id}.log.json для записи логов контейнера {container.name} c id: {container.short_id}');
                with open(f'{sys.path[0]}/support_logs/{container.name}.{container.short_id}.log.json', 'wb') as file:
                    self.logger.info(f'Произвожу сбор логов у контейнера {container.name} c id: {container.short_id}');
                    try:
                        logs = container.logs(timestamps = True);
                        file.write(logs);
                        self.logger.info(f'Сохранены логи контейнера {container.name} c id: {container.short_id} в {sys.path[0]}/support_logs/{container.name}.{container.short_id}.log.json');
                    except:
                        self.logger.error(f'Произошла ошибка при выгрузке логов из контейнера {container.name} с id: {container.short_id}');
        except:
            self.logger.error(f'Произошла ошибка при выгрузке логов из контейнеров');

        listfiles = []
        for root, dirs, files in os.walk(f"{sys.path[0]}/support_logs"):
            for file in files:
                fpath = os.path.join(root, file)
                listfiles.append(fpath)

        try:
            with tarfile.open("logs.tar.gz", "w:gz") as tar:
                for file in listfiles:
                    onlyfile = os.path.basename(file)
                    tar.add(file, arcname=onlyfile)
                    
        except Exception as e:
            self.form.msgbox(f"Произошла ошибка при архивировании: {e}")
