mirror of
https://github.com/servo/servo.git
synced 2025-07-11 17:33:47 +01:00
252 lines
6.2 KiB
Python
252 lines
6.2 KiB
Python
from copy import copy
|
|
from six import iteritems
|
|
from six.moves.urllib.parse import urljoin, urlparse
|
|
from abc import ABCMeta, abstractproperty
|
|
|
|
MYPY = False
|
|
if MYPY:
|
|
# MYPY is set to True when run under Mypy.
|
|
from typing import Optional
|
|
|
|
item_types = {}
|
|
|
|
|
|
class ManifestItemMeta(ABCMeta):
|
|
"""Custom metaclass that registers all the subclasses in the
|
|
item_types dictionary according to the value of their item_type
|
|
attribute, and otherwise behaves like an ABCMeta."""
|
|
|
|
def __new__(cls, name, bases, attrs, **kwargs):
|
|
rv = ABCMeta.__new__(cls, name, bases, attrs, **kwargs)
|
|
if rv.item_type:
|
|
item_types[rv.item_type] = rv
|
|
|
|
return rv
|
|
|
|
|
|
class ManifestItem(object):
|
|
__metaclass__ = ManifestItemMeta
|
|
|
|
__slots__ = ("_tests_root", "path")
|
|
|
|
item_type = None # type: Optional[str]
|
|
|
|
def __init__(self, tests_root=None, path=None):
|
|
self._tests_root = tests_root
|
|
self.path = path
|
|
|
|
@abstractproperty
|
|
def id(self):
|
|
"""The test's id (usually its url)"""
|
|
pass
|
|
|
|
def key(self):
|
|
"""A unique identifier for the test"""
|
|
return (self.item_type, self.id)
|
|
|
|
def __eq__(self, other):
|
|
if not hasattr(other, "key"):
|
|
return False
|
|
return self.key() == other.key()
|
|
|
|
def __hash__(self):
|
|
return hash(self.key())
|
|
|
|
def __repr__(self):
|
|
return "<%s.%s id=%s, path=%s>" % (self.__module__, self.__class__.__name__, self.id, self.path)
|
|
|
|
def to_json(self):
|
|
return [{}]
|
|
|
|
@classmethod
|
|
def from_json(cls, manifest, path, obj):
|
|
return cls(manifest.tests_root, path)
|
|
|
|
|
|
class URLManifestItem(ManifestItem):
|
|
__slots__ = ("url_base", "_url", "_extras")
|
|
|
|
def __init__(self, tests_root, path, url_base, url, **extras):
|
|
super(URLManifestItem, self).__init__(tests_root, path)
|
|
assert url_base[0] == "/"
|
|
self.url_base = url_base
|
|
assert url[0] != "/"
|
|
self._url = url
|
|
self._extras = extras
|
|
|
|
@property
|
|
def id(self):
|
|
return self.url
|
|
|
|
@property
|
|
def url(self):
|
|
# we can outperform urljoin, because we know we just have path relative URLs
|
|
if self.url_base == "/":
|
|
return "/" + self._url
|
|
return urljoin(self.url_base, self._url)
|
|
|
|
@property
|
|
def https(self):
|
|
flags = set(urlparse(self.url).path.rsplit("/", 1)[1].split(".")[1:-1])
|
|
return ("https" in flags or "serviceworker" in flags)
|
|
|
|
def to_json(self):
|
|
rv = [self._url, {}]
|
|
return rv
|
|
|
|
@classmethod
|
|
def from_json(cls, manifest, path, obj):
|
|
url, extras = obj
|
|
return cls(manifest.tests_root,
|
|
path,
|
|
manifest.url_base,
|
|
url,
|
|
**extras)
|
|
|
|
|
|
class TestharnessTest(URLManifestItem):
|
|
item_type = "testharness"
|
|
|
|
@property
|
|
def timeout(self):
|
|
return self._extras.get("timeout")
|
|
|
|
@property
|
|
def testdriver(self):
|
|
return self._extras.get("testdriver")
|
|
|
|
@property
|
|
def jsshell(self):
|
|
return self._extras.get("jsshell")
|
|
|
|
@property
|
|
def script_metadata(self):
|
|
return self._extras.get("script_metadata")
|
|
|
|
def to_json(self):
|
|
rv = super(TestharnessTest, self).to_json()
|
|
if self.timeout is not None:
|
|
rv[-1]["timeout"] = self.timeout
|
|
if self.testdriver:
|
|
rv[-1]["testdriver"] = self.testdriver
|
|
if self.jsshell:
|
|
rv[-1]["jsshell"] = True
|
|
if self.script_metadata:
|
|
rv[-1]["script_metadata"] = self.script_metadata
|
|
return rv
|
|
|
|
|
|
class RefTestBase(URLManifestItem):
|
|
__slots__ = ("references",)
|
|
|
|
item_type = "reftest_base"
|
|
|
|
def __init__(self, tests_root, path, url_base, url, references=None, **extras):
|
|
super(RefTestBase, self).__init__(tests_root, path, url_base, url, **extras)
|
|
if references is None:
|
|
self.references = []
|
|
else:
|
|
self.references = references
|
|
|
|
@property
|
|
def timeout(self):
|
|
return self._extras.get("timeout")
|
|
|
|
@property
|
|
def viewport_size(self):
|
|
return self._extras.get("viewport_size")
|
|
|
|
@property
|
|
def dpi(self):
|
|
return self._extras.get("dpi")
|
|
|
|
@property
|
|
def fuzzy(self):
|
|
rv = self._extras.get("fuzzy", [])
|
|
if isinstance(rv, list):
|
|
return {tuple(item[0]): item[1]
|
|
for item in self._extras.get("fuzzy", [])}
|
|
return rv
|
|
|
|
def to_json(self):
|
|
rv = [self._url, self.references, {}]
|
|
extras = rv[-1]
|
|
if self.timeout is not None:
|
|
extras["timeout"] = self.timeout
|
|
if self.viewport_size is not None:
|
|
extras["viewport_size"] = self.viewport_size
|
|
if self.dpi is not None:
|
|
extras["dpi"] = self.dpi
|
|
if self.fuzzy:
|
|
extras["fuzzy"] = list(iteritems(self.fuzzy))
|
|
return rv
|
|
|
|
@classmethod
|
|
def from_json(cls, manifest, path, obj):
|
|
url, references, extras = obj
|
|
return cls(manifest.tests_root,
|
|
path,
|
|
manifest.url_base,
|
|
url,
|
|
references,
|
|
**extras)
|
|
|
|
def to_RefTest(self):
|
|
if type(self) == RefTest:
|
|
return self
|
|
rv = copy(self)
|
|
rv.__class__ = RefTest
|
|
return rv
|
|
|
|
def to_RefTestNode(self):
|
|
if type(self) == RefTestNode:
|
|
return self
|
|
rv = copy(self)
|
|
rv.__class__ = RefTestNode
|
|
return rv
|
|
|
|
|
|
class RefTestNode(RefTestBase):
|
|
item_type = "reftest_node"
|
|
|
|
|
|
class RefTest(RefTestBase):
|
|
item_type = "reftest"
|
|
|
|
|
|
class ManualTest(URLManifestItem):
|
|
item_type = "manual"
|
|
|
|
|
|
class ConformanceCheckerTest(URLManifestItem):
|
|
item_type = "conformancechecker"
|
|
|
|
|
|
class VisualTest(URLManifestItem):
|
|
item_type = "visual"
|
|
|
|
|
|
class Stub(URLManifestItem):
|
|
item_type = "stub"
|
|
|
|
|
|
class WebDriverSpecTest(URLManifestItem):
|
|
item_type = "wdspec"
|
|
|
|
@property
|
|
def timeout(self):
|
|
return self._extras.get("timeout")
|
|
|
|
def to_json(self):
|
|
rv = super(WebDriverSpecTest, self).to_json()
|
|
if self.timeout is not None:
|
|
rv[-1]["timeout"] = self.timeout
|
|
return rv
|
|
|
|
|
|
class SupportFile(ManifestItem):
|
|
item_type = "support"
|
|
|
|
@property
|
|
def id(self):
|
|
return self.path
|