import logging import os from celery import shared_task from django.conf import settings from django.contrib.auth.models import User from django.core.cache import caches from devices.constants import CACHE_TIMEOUT from devices.enums import ArmaIndustrialFirewallStatus from devices.models.firewall import ArmaIndustrialFirewall from devices.services.firewall import FirewallService from devices.services.firewall.firewall import firewalls_status_notification_to_ws from storage.models import DataStorage, get_storage_path _log = logging.getLogger(__name__) MEDIA_ROOT = getattr(settings, 'MEDIA_ROOT') @shared_task def update_firewall_info_task(): update_firewall_info() def update_firewall_info(): for firewall in ArmaIndustrialFirewall.objects.all(): info = FirewallService(firewall).get_info() ret, status = {'data': info.get('data', info)}, info.get('status', ArmaIndustrialFirewallStatus.error) def set_firewall_status(firewall_status, firewall_pk): response_json = { 'status': firewall_status } caches['redis'].set(f'firewall_{firewall_pk}_status', response_json, CACHE_TIMEOUT) if status == ArmaIndustrialFirewallStatus.online: set_firewall_status('online', firewall.pk) firewall.website = ret['data']['product_website'] firewall.version = ret['data']['product_version'] firewall.remote_name = ret['data']['product_name'] firewall.identification_number = ret['data']['product_id'] firewall.hash_number = ret['data']['product_hash'] firewall.flavour = ret['data']['product_flavour'] firewall.email = ret['data']['product_email'] firewall.copyright_years = ret['data']['product_copyright_years'] firewall.copyright_url = ret['data']['product_copyright_url'] firewall.copyright_owner = ret['data']['product_copyright_owner'] firewall.architecture = ret['data']['product_arch'] firewall.abi = ret['data']['product_abi'] firewall.save() elif status == ArmaIndustrialFirewallStatus.offline: set_firewall_status('offline', firewall.pk) elif status == ArmaIndustrialFirewallStatus.unauthorized: set_firewall_status('unauthorized', firewall.pk) else: set_firewall_status('error', firewall.pk) firewalls_status_notification_to_ws() @shared_task def download_files_from_firewall_task(firewall_pk: int, user_pk: int, type_file: str): firewall = ArmaIndustrialFirewall.objects.get(pk=firewall_pk) user = User.objects.get(pk=user_pk) _log.debug(f'[TASK] Start download firewall-{firewall.pk} {type_file}. User: {user}') return download_files_from_firewall(firewall, user, type_file) def download_files_from_firewall(firewall: ArmaIndustrialFirewall, user: 'User', type_file: str) -> int: """Скачивания файла с фаервола и сохранения его в локальное Хранилище.""" _log.debug('[download_files_from_firewall] start') format_map = {'rulesets': DataStorage.Format.TAR, 'config': DataStorage.Format.XML} store = DataStorage(type=DataStorage.Type.FIREWALL, format=format_map.get(type_file, DataStorage.Format.UNKNOWN), user=user, description=f'{type_file} from {firewall.name} firewall', file='firewall', size=0) store.save() _log.debug(f'[download_files_from_firewall] create storage [{store.pk}]') file_byte, name = FirewallService(firewall).download_file(type_file) _log.debug(f'[download_files_from_firewall] get file {name}') file_name = get_storage_path(store, name) file_path = os.path.join(MEDIA_ROOT, file_name) os.makedirs(os.path.dirname(file_path), exist_ok=True) _log.debug(f'[download_files_from_firewall] create file {file_path}') with open(file_path, 'wb') as file: file.write(file_byte) store.file = file_name store.size = os.path.getsize(file_path) store.save() _log.debug(f'[download_files_from_firewall] finish.') return store.pk