Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(84)

Side by Side Diff: third_party/WebKit/Tools/Scripts/webkitpy/w3c/test_importer.py

Issue 2652653011: Rename update_w3c_test_expectations and related files. (Closed)
Patch Set: Rebase, add back accidentally-removed "directory owner extractor" code Created 3 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 # Copyright 2014 The Chromium Authors. All rights reserved. 1 # Copyright 2014 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be 2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file. 3 # found in the LICENSE file.
4 4
5 """Fetches a copy of the latest state of a W3C test repository and commits. 5 """Fetches a copy of the latest state of a W3C test repository and commits.
6 6
7 If this script is given the argument --auto-update, it will also: 7 If this script is given the argument --auto-update, it will also:
8 1. Upload a CL. 8 1. Upload a CL.
9 2. Trigger try jobs and wait for them to complete. 9 2. Trigger try jobs and wait for them to complete.
10 3. Make any changes that are required for new failing tests. 10 3. Make any changes that are required for new failing tests.
11 4. Commit the CL. 11 4. Commit the CL.
12 12
13 If this script is given the argument --auto-update, it will also attempt to 13 If this script is given the argument --auto-update, it will also attempt to
14 upload a CL, trigger try jobs, and make any changes that are required for 14 upload a CL, trigger try jobs, and make any changes that are required for
15 new failing tests before committing. 15 new failing tests before committing.
16 """ 16 """
17 17
18 import argparse 18 import argparse
19 import json 19 import json
20 import logging 20 import logging
21 import re 21 import re
22 22
23 from webkitpy.common.net.git_cl import GitCL 23 from webkitpy.common.net.git_cl import GitCL
24 from webkitpy.common.webkit_finder import WebKitFinder 24 from webkitpy.common.webkit_finder import WebKitFinder
25 from webkitpy.layout_tests.models.test_expectations import TestExpectations, Tes tExpectationParser 25 from webkitpy.layout_tests.models.test_expectations import TestExpectations, Tes tExpectationParser
26 from webkitpy.w3c.update_w3c_test_expectations import W3CExpectationsLineAdder 26 from webkitpy.w3c.common import WPT_REPO_URL, CSS_REPO_URL, WPT_DEST_NAME, CSS_D EST_NAME
27 from webkitpy.w3c.directory_owners_extractor import DirectoryOwnersExtractor
27 from webkitpy.w3c.test_copier import TestCopier 28 from webkitpy.w3c.test_copier import TestCopier
28 from webkitpy.w3c.common import WPT_REPO_URL, CSS_REPO_URL, WPT_DEST_NAME, CSS_D EST_NAME 29 from webkitpy.w3c.wpt_expectations_updater import WPTExpectationsUpdater
29 30
30 # Settings for how often to check try job results and how long to wait. 31 # Settings for how often to check try job results and how long to wait.
31 POLL_DELAY_SECONDS = 2 * 60 32 POLL_DELAY_SECONDS = 2 * 60
32 TIMEOUT_SECONDS = 180 * 60 33 TIMEOUT_SECONDS = 180 * 60
33 34
34 _log = logging.getLogger(__file__) 35 _log = logging.getLogger(__file__)
35 36
36 37
37 class TestImporter(object): 38 class TestImporter(object):
38 39
(...skipping 278 matching lines...) Expand 10 before | Expand all | Expand 10 after
317 if self.git_cl.has_failing_try_results(try_results): 318 if self.git_cl.has_failing_try_results(try_results):
318 _log.info('CQ failed; aborting.') 319 _log.info('CQ failed; aborting.')
319 self.git_cl.run(['set-close']) 320 self.git_cl.run(['set-close'])
320 return False 321 return False
321 322
322 _log.info('Update completed.') 323 _log.info('Update completed.')
323 return True 324 return True
324 325
325 def _upload_cl(self): 326 def _upload_cl(self):
326 _log.info('Uploading change list.') 327 _log.info('Uploading change list.')
327 cc_list = self.get_directory_owners_to_cc() 328 cc_list = self.get_directory_owners()
328 description = self._cl_description() 329 description = self._cl_description()
329 self.git_cl.run([ 330 self.git_cl.run([
330 'upload', 331 'upload',
331 '-f', 332 '-f',
332 '--rietveld', 333 '--rietveld',
333 '-m', 334 '-m',
334 description, 335 description,
335 ] + ['--cc=' + email for email in cc_list]) 336 ] + ['--cc=' + email for email in cc_list])
336 337
338 def get_directory_owners(self):
339 """Returns a list of email addresses of owners of changed tests."""
340 _log.info('Gathering directory owners emails to CC.')
341 changed_files = self.host.cwd().changed_files()
342 extractor = DirectoryOwnersExtractor(self.fs)
343 extractor.read_owner_map()
344 return extractor.list_owners(changed_files)
345
337 def _cl_description(self): 346 def _cl_description(self):
338 description = self.check_run(['git', 'log', '-1', '--format=%B']) 347 description = self.check_run(['git', 'log', '-1', '--format=%B'])
339 build_link = self._build_link() 348 build_link = self._build_link()
340 if build_link: 349 if build_link:
341 description += 'Build: %s\n\n' % build_link 350 description += 'Build: %s\n\n' % build_link
342 description += 'TBR=qyearsley@chromium.org\n' 351 description += 'TBR=qyearsley@chromium.org\n'
343 # Move any NOEXPORT tag to the end of the description. 352 # Move any NOEXPORT tag to the end of the description.
344 description = description.replace('NOEXPORT=true', '') 353 description = description.replace('NOEXPORT=true', '')
345 description = description.replace('\n\n\n\n', '\n\n') 354 description = description.replace('\n\n\n\n', '\n\n')
346 description += 'NOEXPORT=true' 355 description += 'NOEXPORT=true'
347 return description 356 return description
348 357
349 def _build_link(self): 358 def _build_link(self):
350 """Returns a link to a job, if running on buildbot.""" 359 """Returns a link to a job, if running on buildbot."""
351 master_name = self.host.environ.get('BUILDBOT_MASTERNAME') 360 master_name = self.host.environ.get('BUILDBOT_MASTERNAME')
352 builder_name = self.host.environ.get('BUILDBOT_BUILDERNAME') 361 builder_name = self.host.environ.get('BUILDBOT_BUILDERNAME')
353 build_number = self.host.environ.get('BUILDBOT_BUILDNUMBER') 362 build_number = self.host.environ.get('BUILDBOT_BUILDNUMBER')
354 if not (master_name and builder_name and build_number): 363 if not (master_name and builder_name and build_number):
355 return None 364 return None
356 return 'https://build.chromium.org/p/%s/builders/%s/builds/%s' % (master _name, builder_name, build_number) 365 return 'https://build.chromium.org/p/%s/builders/%s/builds/%s' % (master _name, builder_name, build_number)
357 366
358 def get_directory_owners_to_cc(self):
359 """Returns a list of email addresses to CC for the current import."""
360 _log.info('Gathering directory owners emails to CC.')
361 directory_owners_file_path = self.finder.path_from_webkit_base(
362 'Tools', 'Scripts', 'webkitpy', 'w3c', 'directory_owners.json')
363 with open(directory_owners_file_path) as data_file:
364 directory_to_owner = self.parse_directory_owners(json.load(data_file ))
365 out = self.check_run(['git', 'diff', 'origin/master', '--name-only'])
366 changed_files = out.splitlines()
367 return self.generate_email_list(changed_files, directory_to_owner)
368
369 @staticmethod
370 def parse_directory_owners(decoded_data_file):
371 directory_dict = {}
372 for dict_set in decoded_data_file:
373 if dict_set['notification-email']:
374 directory_dict[dict_set['directory']] = dict_set['notification-e mail']
375 return directory_dict
376
377 def generate_email_list(self, changed_files, directory_to_owner):
378 """Returns a list of email addresses based on the given file list and
379 directory-to-owner mapping.
380
381 Args:
382 changed_files: A list of file paths relative to the repository root.
383 directory_to_owner: A dict mapping layout test directories to emails .
384
385 Returns:
386 A list of the email addresses to be notified for the current import.
387 """
388 email_addresses = set()
389 for file_path in changed_files:
390 test_path = self.finder.layout_test_name(file_path)
391 if test_path is None:
392 continue
393 test_dir = self.fs.dirname(test_path)
394 if test_dir in directory_to_owner:
395 address = directory_to_owner[test_dir]
396 if not re.match(r'\S+@\S+', address):
397 _log.warning('%s appears not be an email address, skipping.' , address)
398 continue
399 email_addresses.add(address)
400 return sorted(email_addresses)
401
402 def fetch_new_expectations_and_baselines(self): 367 def fetch_new_expectations_and_baselines(self):
403 """Adds new expectations and downloads baselines based on try job result s, then commits and uploads the change.""" 368 """Adds new expectations and downloads baselines based on try job result s, then commits and uploads the change."""
404 _log.info('Adding test expectations lines to LayoutTests/TestExpectation s.') 369 _log.info('Adding test expectations lines to LayoutTests/TestExpectation s.')
405 line_adder = W3CExpectationsLineAdder(self.host) 370 line_adder = WPTExpectationsUpdater(self.host)
406 line_adder.run() 371 line_adder.run()
407 message = 'Update test expectations and baselines.' 372 message = 'Update test expectations and baselines.'
408 self.check_run(['git', 'commit', '-a', '-m', message]) 373 self.check_run(['git', 'commit', '-a', '-m', message])
409 self.git_cl.run(['upload', '-m', message, '--rietveld']) 374 self.git_cl.run(['upload', '-m', message, '--rietveld'])
410 375
411 def update_all_test_expectations_files(self, deleted_tests, renamed_tests): 376 def update_all_test_expectations_files(self, deleted_tests, renamed_tests):
412 """Updates all test expectations files for tests that have been deleted or renamed.""" 377 """Updates all test expectations files for tests that have been deleted or renamed."""
413 port = self.host.port_factory.get() 378 port = self.host.port_factory.get()
414 for path, file_contents in port.all_expectations_dict().iteritems(): 379 for path, file_contents in port.all_expectations_dict().iteritems():
415 parser = TestExpectationParser(port, all_tests=None, is_lint_mode=Fa lse) 380 parser = TestExpectationParser(port, all_tests=None, is_lint_mode=Fa lse)
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
451 """Returns a dict mapping source to dest name for layout tests that have been renamed.""" 416 """Returns a dict mapping source to dest name for layout tests that have been renamed."""
452 out = self.check_run(['git', 'diff', 'origin/master', '-M100%', '--diff- filter=R', '--name-status']) 417 out = self.check_run(['git', 'diff', 'origin/master', '-M100%', '--diff- filter=R', '--name-status'])
453 renamed_tests = {} 418 renamed_tests = {}
454 for line in out.splitlines(): 419 for line in out.splitlines():
455 _, source_path, dest_path = line.split() 420 _, source_path, dest_path = line.split()
456 source_test = self.finder.layout_test_name(source_path) 421 source_test = self.finder.layout_test_name(source_path)
457 dest_test = self.finder.layout_test_name(dest_path) 422 dest_test = self.finder.layout_test_name(dest_path)
458 if source_test and dest_test: 423 if source_test and dest_test:
459 renamed_tests[source_test] = dest_test 424 renamed_tests[source_test] = dest_test
460 return renamed_tests 425 return renamed_tests
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698