blob: 6bbab35dfdef00d3910ee108cc558837d65f6d2c [file] [log] [blame]
Milan Verespej2e1328a2019-06-18 13:40:08 +02001# -*- coding: utf-8 -*-
2
3# COPYRIGHT NOTICE STARTS HERE
4
5# Copyright 2019 © Samsung Electronics Co., Ltd.
6#
7# Licensed under the Apache License, Version 2.0 (the "License");
8# you may not use this file except in compliance with the License.
9# You may obtain a copy of the License at
10#
11# http://www.apache.org/licenses/LICENSE-2.0
12#
13# Unless required by applicable law or agreed to in writing, software
14# distributed under the License is distributed on an "AS IS" BASIS,
15# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16# See the License for the specific language governing permissions and
17# limitations under the License.
18
19# COPYRIGHT NOTICE ENDS HERE
20
21import logging
22from abc import ABC, abstractmethod
23
24import prettytable
25
26log = logging.getLogger(__name__)
27
28
29class AbstractDownloader(ABC):
30
31 def __init__(self, list_type, *list_args):
32 self._list_type = list_type
33 self._data_list = {item: list_arg[1] for list_arg in list_args
Milan Verespej477d8ad2019-07-02 11:00:29 +020034 for item in self.load_list(list_arg[0])}
Milan Verespej2e1328a2019-06-18 13:40:08 +020035 self._missing = self.missing()
36
37 @property
38 def list_type(self):
39 """
40 Type of resource in list
41 """
42 return self._list_type
43
44 @staticmethod
Milan Verespej477d8ad2019-07-02 11:00:29 +020045 def load_list(path):
Milan Verespej2e1328a2019-06-18 13:40:08 +020046 """
47 Load list from file.
48 :param path: path to file
49 :return: set of items in list
50 """
51 with open(path, 'r') as f:
52 return {item for item in (line.strip() for line in f)
53 if item and not item.startswith('#')}
54
55 @staticmethod
56 def _check_table(header, alignment_dict, data):
57 """
58 General method to generate table
59 :param header: header of the table
60 :param alignment_dict: dictionary with alignment for columns
61 :param data: iterable of rows of table
62 :return: table formatted data
63 """
64 table = prettytable.PrettyTable(header)
65
66 for k, v in alignment_dict.items():
67 table.align[k] = v
68
69 for row in sorted(data):
70 table.add_row(row)
71
72 return table
73
74 @abstractmethod
75 def download(self):
76 """
77 Download resources from lists
78 """
79 pass
80
81 @abstractmethod
82 def _is_missing(self, item):
83 """
84 Check if item is not downloaded
85 """
86 pass
87
88 def missing(self):
89 """
90 Check for missing data (not downloaded)
91 :return: dictionary of missing items
92 """
93 self._missing = {item: dst for item, dst in self._data_list.items() if
94 self._is_missing(item)}
95 return self._missing
96
97 def _log_existing(self):
98 """
99 Log items that are already downloaded.
100 """
101 for item in self._merged_lists():
102 if item not in self._missing:
Milan Verespejda9e6b92019-06-18 15:09:41 +0200103 if type(self).__name__ == 'DockerDownloader':
104 log.info('Docker image present: {}'.format(item))
105 else:
106 log.info('File or directory present: {}'.format(item))
Milan Verespej2e1328a2019-06-18 13:40:08 +0200107
108 def _merged_lists(self):
109 """
110 Get all item names in one set
111 :return: set with all items
112 """
113 return set(self._data_list.keys())
114
115 def _initial_log(self):
116 """
117 Log initial info for download.
118 :return: True if download is necessary False if everything is already downloaded
119 """
120 self._log_existing()
121 items_left = len(self._missing)
122 class_name = type(self).__name__
123 if items_left == 0:
124 log.info('{}: Everything seems to be present no download necessary.'.format(class_name))
125 return False
126 log.info('{}: Initializing download {} {} are not present.'.format(class_name, items_left,
127 self._list_type))
128 return True