#!/usr/bin/python """ Copyright 2014 Google Inc. Use of this source code is governed by a BSD-style license that can be found in the LICENSE file. ImagePair class (see class docstring for details) """ import posixpath # Keys used within ImagePair dictionary representations. KEY_DIFFERENCE_DATA = 'differenceData' KEY_EXPECTATIONS_DATA = 'expectationsData' KEY_EXTRA_COLUMN_VALUES = 'extraColumnValues' KEY_IMAGE_A_URL = 'imageAUrl' KEY_IMAGE_B_URL = 'imageBUrl' KEY_IS_DIFFERENT = 'isDifferent' class ImagePair(object): """ Describes a pair of images, along with optional metadata (pixel difference metrics, whether to ignore mismatches, etc.) """ def __init__(self, image_diff_db, base_url, imageA_relative_url, imageB_relative_url, expectations=None, extra_columns=None): """ Args: image_diff_db: ImageDiffDB instance we use to generate/store image diffs base_url: base of all image URLs imageA_relative_url: URL pointing at an image, relative to base_url imageB_relative_url: URL pointing at an image, relative to base_url expectations: optional dictionary containing expectations-specific metadata (ignore-failure, bug numbers, etc.) extra_columns: optional dictionary containing more metadata (test name, builder name, etc.) """ self.base_url = base_url self.imageA_relative_url = imageA_relative_url self.imageB_relative_url = imageB_relative_url self.expectations_dict = expectations self.extra_columns_dict = extra_columns if imageA_relative_url == imageB_relative_url: self.diff_record = None else: # TODO(epoger): Rather than blocking until image_diff_db can read in # the image pair and generate diffs, it would be better to do it # asynchronously: tell image_diff_db to download a bunch of file pairs, # and only block later if we're still waiting for diff_records to come # back. image_diff_db.add_image_pair( expected_image_locator=imageA_relative_url, expected_image_url=posixpath.join(base_url, imageA_relative_url), actual_image_locator=imageB_relative_url, actual_image_url=posixpath.join(base_url, imageB_relative_url)) self.diff_record = image_diff_db.get_diff_record( expected_image_locator=imageA_relative_url, actual_image_locator=imageB_relative_url) def as_dict(self): """ Return a dictionary describing this ImagePair, as needed when constructing the JSON representation. Uses the KEY_* constants as keys. """ asdict = { KEY_IMAGE_A_URL: self.imageA_relative_url, KEY_IMAGE_B_URL: self.imageB_relative_url, } if self.expectations_dict: asdict[KEY_EXPECTATIONS_DATA] = self.expectations_dict if self.extra_columns_dict: asdict[KEY_EXTRA_COLUMN_VALUES] = self.extra_columns_dict if self.diff_record and (self.diff_record.get_num_pixels_differing() > 0): asdict[KEY_IS_DIFFERENT] = True asdict[KEY_DIFFERENCE_DATA] = self.diff_record.as_dict() else: asdict[KEY_IS_DIFFERENT] = False return asdict