Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 # Copyright (c) 2012 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 from datetime import datetime | |
| 5 import glob | |
| 6 import os | |
| 7 import re | |
| 8 | |
| 4 from telemetry import test | 9 from telemetry import test |
| 10 from telemetry.core.backends import png_bitmap | |
| 5 from telemetry.page import page_test | 11 from telemetry.page import page_test |
| 6 | 12 |
| 13 test_data_dir = os.path.abspath(os.path.join( | |
|
Zhenyao Mo
2013/09/05 00:23:14
The reason we use a passed in dir is because the s
| |
| 14 os.path.dirname(__file__), '..', '..', 'data', 'gpu')) | |
| 15 | |
| 16 generated_data_dir = os.path.join(test_data_dir, 'generated') | |
| 17 ref_image_dir = os.path.join(test_data_dir, 'gpu_reference') | |
|
Ken Russell (switch to Gerrit)
2013/09/05 00:27:04
The current harness is careful not to dump images
| |
| 7 | 18 |
| 8 class PixelTestFailure(Exception): | 19 class PixelTestFailure(Exception): |
| 9 pass | 20 pass |
| 10 | 21 |
| 11 | |
| 12 class PixelValidator(page_test.PageTest): | 22 class PixelValidator(page_test.PageTest): |
| 13 def __init__(self): | 23 def __init__(self): |
| 14 super(PixelValidator, self).__init__('ValidatePage') | 24 super(PixelValidator, self).__init__('ValidatePage') |
| 15 | 25 |
| 26 def CustomizeBrowserOptions(self, options): | |
| 27 options.AppendExtraBrowserArg('--enable-gpu-benchmarking') | |
| 28 | |
| 16 def ValidatePage(self, page, tab, results): | 29 def ValidatePage(self, page, tab, results): |
| 17 # TODO(bajones): Grab screenshot, compare to reference. | 30 if not tab.screenshot_supported: |
| 18 # page.reference_image | 31 raise page_test.Failure("Browser does not support screenshot capture") |
| 19 pass | |
| 20 | 32 |
| 33 screenshot = tab.Screenshot(5) | |
| 34 | |
| 35 if not screenshot: | |
| 36 raise page_test.Failure("Could not capture screenshot") | |
| 37 | |
| 38 image_name = PixelValidator.UrlToImageName(page.url) | |
| 39 | |
| 40 ref_png = PixelValidator.GetReferenceImage(image_name, page.revision, | |
| 41 screenshot) | |
| 42 | |
| 43 # Test new snapshot against existing reference image | |
| 44 if not ref_png.IsEqual(screenshot, tolerance=2): | |
| 45 PixelValidator.WriteErrorImages(image_name, page.revision, screenshot, | |
| 46 ref_png) | |
| 47 raise page_test.Failure("Reference image did not match captured screen") | |
| 48 | |
| 49 @staticmethod | |
| 50 def UrlToImageName(url): | |
| 51 image_name = re.sub(r'^(http|https|file)://(/*)', '', url) | |
| 52 image_name = re.sub(r'\.\./', '', image_name) | |
| 53 image_name = re.sub(r'(\.|/|-)', '_', image_name) | |
| 54 return image_name | |
| 55 | |
| 56 @staticmethod | |
| 57 def DeleteOldReferenceImages(ref_image_path, cur_revision): | |
| 58 if not cur_revision: | |
| 59 return | |
| 60 | |
| 61 old_revisions = glob.glob(ref_image_path + "__rev_*.png") | |
| 62 for rev_path in old_revisions: | |
| 63 m = re.match(r'^.*__rev_(\d+)\.png$', rev_path) | |
| 64 if m and int(m.group(1)) < cur_revision: | |
| 65 print 'Found deprecated reference image. Deleting rev ' + m.group(1) | |
| 66 os.remove(rev_path) | |
| 67 | |
| 68 @staticmethod | |
| 69 def GetReferenceImage(image_name, cur_revision, screenshot): | |
| 70 if not cur_revision: | |
| 71 cur_revision = 0 | |
| 72 | |
| 73 image_path = os.path.join(ref_image_dir, image_name) | |
| 74 | |
| 75 PixelValidator.DeleteOldReferenceImages(image_path, cur_revision) | |
| 76 | |
| 77 image_path = image_path + '__rev_' + str(cur_revision) + '.png' | |
| 78 | |
| 79 try: | |
| 80 ref_png = png_bitmap.PngBitmap.FromFile(image_path) | |
| 81 except IOError: | |
| 82 ref_png = None | |
| 83 | |
| 84 if ref_png: | |
| 85 return ref_png | |
| 86 | |
| 87 print 'Reference image not found. Writing tab contents as reference.' | |
| 88 | |
| 89 PixelValidator.WriteImage(image_path, screenshot) | |
| 90 return screenshot | |
| 91 | |
| 92 @staticmethod | |
| 93 def WriteErrorImages(image_name, cur_revision, screenshot, ref_png): | |
| 94 capture_time = datetime.now() | |
| 95 full_image_name = image_name + '__rev_' + str(cur_revision) | |
| 96 full_image_name = full_image_name + capture_time.strftime("__%b%d_%H_%M_%S") | |
| 97 full_image_name = full_image_name + '.png' | |
| 98 | |
| 99 PixelValidator.WriteImage( | |
| 100 os.path.join(generated_data_dir, 'FAIL_' + full_image_name), screenshot) | |
| 101 | |
| 102 diff_png = screenshot.Diff(ref_png) | |
| 103 PixelValidator.WriteImage( | |
| 104 os.path.join(generated_data_dir, 'DIFF_' + full_image_name), diff_png) | |
| 105 | |
| 106 @staticmethod | |
| 107 def WriteImage(image_path, png_image): | |
| 108 output_dir = os.path.dirname(image_path) | |
| 109 if not os.path.exists(output_dir): | |
| 110 os.makedirs(output_dir) | |
| 111 | |
| 112 png_image.WriteFile(image_path) | |
| 21 | 113 |
| 22 class Pixel(test.Test): | 114 class Pixel(test.Test): |
| 23 enabled = False | 115 enabled = False |
| 24 test = PixelValidator | 116 test = PixelValidator |
| 25 page_set = 'page_sets/pixel_tests.json' | 117 page_set = 'page_sets/pixel_tests.json' |
| OLD | NEW |