1 # -*- encoding: latin-1 -*- |
|
2 |
|
3 #============================================================================ |
|
4 #Name : MattiDrops.py |
|
5 #Part of : Helium |
|
6 |
|
7 #Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). |
|
8 #All rights reserved. |
|
9 #This component and the accompanying materials are made available |
|
10 #under the terms of the License "Eclipse Public License v1.0" |
|
11 #which accompanies this distribution, and is available |
|
12 #at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
13 # |
|
14 #Initial Contributors: |
|
15 #Nokia Corporation - initial contribution. |
|
16 # |
|
17 #Contributors: |
|
18 # |
|
19 #Description: Script for test drop generation and sending to execution to |
|
20 #ATS3-system |
|
21 #=============================================================================== |
|
22 |
|
23 """ create the MATTI test drop file for use on the test server """ |
|
24 # pylint: disable=R0902, R0903, R0912 |
|
25 |
|
26 import os |
|
27 import re |
|
28 import sys |
|
29 import string |
|
30 import zipfile |
|
31 import logging |
|
32 from optparse import OptionParser |
|
33 from xml.etree import ElementTree as et |
|
34 from jinja2 import Environment, PackageLoader # pylint: disable=F0401 |
|
35 |
|
36 # Shortcuts |
|
37 E = et.Element |
|
38 SE = et.SubElement |
|
39 |
|
40 _logger = logging.getLogger('matti') |
|
41 |
|
42 class Configuration(object): |
|
43 """ |
|
44 ATS3 drop generation configuration. |
|
45 """ |
|
46 |
|
47 def __init__(self, opts): |
|
48 """ |
|
49 Initialize from optparse configuration options. |
|
50 """ |
|
51 self._opts = opts |
|
52 |
|
53 # Customize some attributes from how optparse leaves them. |
|
54 self.build_drive = os.path.normpath(self._opts.build_drive) |
|
55 self.file_store = os.path.normpath(self._opts.file_store) |
|
56 self.matti_scripts = os.path.normpath(self._opts.matti_scripts) |
|
57 self.template_location = os.path.normpath(self._opts.template_loc) |
|
58 if self._opts.flash_images: |
|
59 self.flash_images = self._opts.flash_images.split(',') |
|
60 else: |
|
61 self.flash_images = [] |
|
62 if not re.search(r'\A\s*?\Z', self._opts.sis_files): |
|
63 self.sis_files = self._opts.sis_files.split(',') |
|
64 else: |
|
65 self.sis_files = None |
|
66 self.step_list = [] |
|
67 self.filelist = [] |
|
68 self.image_list = [] |
|
69 self.sis_list = [] |
|
70 self.device_type = self._opts.device_type |
|
71 self.device_hwid = self._opts.device_hwid |
|
72 self.drop_file = self._opts.drop_file |
|
73 self.minimum_flash_images = self._opts.minimum_flash_images |
|
74 self.plan_name = self._opts.plan_name |
|
75 self.test_timeout = self._opts.test_timeout |
|
76 self.diamonds_build_url = self._opts.diamonds_build_url |
|
77 self.testrun_name = self._opts.testrun_name |
|
78 self.report_email = self._opts.report_email |
|
79 self.harness = self._opts.harness |
|
80 self.sis_enabled = False |
|
81 if self.sis_files: |
|
82 if len(self.sis_files) >= 1: |
|
83 self.sis_enabled = True |
|
84 |
|
85 |
|
86 def __getattr__(self, attr): |
|
87 return getattr(self._opts, attr) |
|
88 |
|
89 def __str__(self): |
|
90 dump = "Configuration:\n" |
|
91 seen = set() |
|
92 for key, value in vars(self).items(): |
|
93 if not key.startswith("_"): |
|
94 dump += "\t%s = %s\n" % (key, value) |
|
95 seen.add(key) |
|
96 for key, value in vars(self._opts).items(): |
|
97 if key not in seen: |
|
98 dump += "\t%s = %s\n" % (key, value) |
|
99 seen.add(key) |
|
100 return dump |
|
101 |
|
102 class MattiDrop(object): |
|
103 """ |
|
104 ATS3 testdrop generation for MATTI tool |
|
105 """ |
|
106 |
|
107 def __init__(self, config=None): |
|
108 self.configuration = config |
|
109 self.matti_cases = {} |
|
110 self.tmp_path = os.getcwd() |
|
111 self.files = [] |
|
112 self.test_files = [] |
|
113 |
|
114 def fetch_testfiles(self): |
|
115 """Needed flash files, sis-files and testscripts from given matti scripts -folder are added to file list.""" |
|
116 tmp_case_list = [] |
|
117 # tmp_image_list = [] |
|
118 os.chdir(os.path.normpath(self.configuration.matti_scripts)) |
|
119 try: |
|
120 for path, _, names in os.walk(os.getcwd()): |
|
121 for name in names: |
|
122 if re.search(r'.*?[.]rb\Z', name): |
|
123 tmp_case_list.append((os.path.normpath(os.path.join(path, name)), os.path.join("ats3", "matti", "script", name))) |
|
124 if tmp_case_list: |
|
125 for tmp_case in tmp_case_list: |
|
126 self.configuration.step_list.append(dict(path=os.path.join("§TEST_RUN_ROOT§", str(tmp_case[1])), name="Test case")) |
|
127 if self.configuration.flash_images: |
|
128 for image in self.configuration.flash_images: |
|
129 tmp = string.rsplit(image, os.sep) |
|
130 image_name = tmp[len(tmp)-1] |
|
131 self.configuration.image_list.append(os.path.join("ATS3Drop", "images", image_name)) |
|
132 if self.configuration.sis_files: |
|
133 for sis in self.configuration.sis_files: |
|
134 tmp = string.rsplit(sis, os.sep) |
|
135 sis_name = tmp[len(tmp)-1] |
|
136 self.configuration.sis_list.append(dict(path=os.path.join("ATS3Drop", "sis", sis_name), dest=sis_name)) |
|
137 except KeyError, error: |
|
138 _logger.error("Error in file reading / fetching!") |
|
139 sys.stderr.write(error) |
|
140 if tmp_case_list: |
|
141 for tmp_case in tmp_case_list: |
|
142 self.configuration.filelist.append(tmp_case[1]) |
|
143 return tmp_case_list |
|
144 else: |
|
145 _logger.error("No test cases/files available!") |
|
146 return None |
|
147 |
|
148 |
|
149 def create_testxml(self): |
|
150 """This method will use Jinja2 template engine for test.xml creation""" |
|
151 os.chdir(self.tmp_path) |
|
152 env = Environment(loader=PackageLoader('ats3.matti', 'template')) |
|
153 if os.path.isfile(self.configuration.template_location): |
|
154 template = env.from_string(open(self.configuration.template_location).read()) |
|
155 xml_file = open("test.xml", 'w') |
|
156 xml_file.write(template.render(configuration=self.configuration)) |
|
157 xml_file.close() |
|
158 else: |
|
159 _logger.error("No template file found") |
|
160 |
|
161 def create_testdrop(self, output_file=None, file_list=None): |
|
162 """Creates testdrop zip-file to given location.""" |
|
163 #env = Environment(loader=PackageLoader('MattiDrops', 'template')) |
|
164 os.chdir(self.tmp_path) |
|
165 if output_file and file_list: |
|
166 zfile = zipfile.ZipFile(output_file, "w", zipfile.ZIP_DEFLATED) |
|
167 try: |
|
168 _logger.info("Adding files to testdrop:") |
|
169 for src_file, drop_file in file_list: |
|
170 _logger.info(" + Adding: %s" % src_file.strip()) |
|
171 if os.path.isfile(src_file): |
|
172 zfile.write(str(src_file.strip()), str(drop_file)) |
|
173 else: |
|
174 _logger.error("invalid test file name supplied %s " % drop_file) |
|
175 if self.configuration.flash_images: |
|
176 for image in self.configuration.flash_images: |
|
177 tmp = string.rsplit(image, os.sep) |
|
178 image_name = tmp[len(tmp)-1] |
|
179 _logger.info(" + Adding: %s" % image_name) |
|
180 if os.path.isfile(image): |
|
181 zfile.write(image, os.path.join("ATS3Drop", "images", image_name)) |
|
182 else: |
|
183 _logger.error("invalid flash file name supplied %s " % image_name) |
|
184 if self.configuration.sis_enabled: |
|
185 if self.configuration.sis_files: |
|
186 for sis in self.configuration.sis_files: |
|
187 tmp = string.rsplit(sis, os.sep) |
|
188 sis_name = tmp[len(tmp)-1] |
|
189 _logger.info(" + Adding: %s" % sis_name) |
|
190 if os.path.isfile(sis): |
|
191 zfile.write(sis, os.path.join("ATS3Drop", "sis", sis_name)) |
|
192 else: |
|
193 _logger.error("invalid sis file name supplied %s " % sis_name) |
|
194 zfile.write(os.path.normpath(os.path.join(os.getcwd(),"test.xml")), "test.xml") |
|
195 finally: |
|
196 _logger.info("Testdrop created! %s" % output_file) |
|
197 zfile.close() |
|
198 return zfile |
|
199 |
|
200 def create_drop(configuration): |
|
201 """Testdrop creation""" |
|
202 if configuration: |
|
203 m_drop = MattiDrop(configuration) |
|
204 m_drop.fetch_testfiles() |
|
205 m_drop.create_testxml() |
|
206 return m_drop.create_testdrop(configuration.drop_file, m_drop.fetch_testfiles()) |
|
207 else: |
|
208 _logger.error("No configuration available for test drop creation") |
|
209 |
|
210 def main(): |
|
211 """Main entry point.""" |
|
212 cli = OptionParser(usage="%prog [options] TSRC1 [TSRC2 [TSRC3 ...]]") |
|
213 cli.add_option("--build-drive", help="Build area root drive", default='X:') |
|
214 cli.add_option("--matti-scripts", help="Path to the directory where the MATTI test scripts are saved.", default="") |
|
215 cli.add_option("--flash-images", help="Flash image files as a list", |
|
216 default="") |
|
217 cli.add_option("--report-email", help="Email notification receivers", |
|
218 default="") |
|
219 cli.add_option("--harness", help="Test harness (default: %default)", |
|
220 default="unknown") |
|
221 cli.add_option("--file-store", help="Destination path for reports.", |
|
222 default="") |
|
223 cli.add_option("--testrun-name", help="Name of the test run", |
|
224 default="run") |
|
225 cli.add_option("--device-type", help="Device type (e.g. 'PRODUCT')", |
|
226 default="unknown") |
|
227 cli.add_option("--device-hwid", help="Device hwid", |
|
228 default="") |
|
229 cli.add_option("--diamonds-build-url", help="Diamonds build url") |
|
230 cli.add_option("--drop-file", help="Name for the final drop zip file", |
|
231 default="") |
|
232 cli.add_option("--minimum-flash-images", help="Minimum amount of flash images", |
|
233 default=2) |
|
234 cli.add_option("--plan-name", help="Name of the test plan", |
|
235 default="plan") |
|
236 cli.add_option("--sis-files", help="Sis files as a list", |
|
237 default="") |
|
238 cli.add_option("--template-loc", help="location of template file", |
|
239 default="..\template") |
|
240 cli.add_option("--test-timeout", help="Test execution timeout value (default: %default)", |
|
241 default="60") |
|
242 cli.add_option("--verbose", help="Increase output verbosity", |
|
243 action="store_true", default=True) |
|
244 opts, _ = cli.parse_args() |
|
245 |
|
246 if opts.verbose: |
|
247 _logger.setLevel(logging.DEBUG) |
|
248 logging.basicConfig(level=logging.DEBUG) |
|
249 config = Configuration(opts) |
|
250 create_drop(config) |
|
251 |
|
252 |
|
253 if __name__ == "__main__": |
|
254 main() |
|