summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/harness/wptrunner/manifestinclude.py
diff options
context:
space:
mode:
authorMatt A. Tobin <mattatobin@localhost.localdomain>2018-02-02 04:16:08 -0500
committerMatt A. Tobin <mattatobin@localhost.localdomain>2018-02-02 04:16:08 -0500
commit5f8de423f190bbb79a62f804151bc24824fa32d8 (patch)
tree10027f336435511475e392454359edea8e25895d /testing/web-platform/harness/wptrunner/manifestinclude.py
parent49ee0794b5d912db1f95dce6eb52d781dc210db5 (diff)
downloadUXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.gz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.lz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.xz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.zip
Add m-esr52 at 52.6.0
Diffstat (limited to 'testing/web-platform/harness/wptrunner/manifestinclude.py')
-rw-r--r--testing/web-platform/harness/wptrunner/manifestinclude.py144
1 files changed, 144 insertions, 0 deletions
diff --git a/testing/web-platform/harness/wptrunner/manifestinclude.py b/testing/web-platform/harness/wptrunner/manifestinclude.py
new file mode 100644
index 000000000..d9b4ee455
--- /dev/null
+++ b/testing/web-platform/harness/wptrunner/manifestinclude.py
@@ -0,0 +1,144 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this file,
+# You can obtain one at http://mozilla.org/MPL/2.0/.
+
+"""Manifest structure used to store paths that should be included in a test run.
+
+The manifest is represented by a tree of IncludeManifest objects, the root
+representing the file and each subnode representing a subdirectory that should
+be included or excluded.
+"""
+import glob
+import os
+import urlparse
+
+from wptmanifest.node import DataNode
+from wptmanifest.backends import conditional
+from wptmanifest.backends.conditional import ManifestItem
+
+
+class IncludeManifest(ManifestItem):
+ def __init__(self, node):
+ """Node in a tree structure representing the paths
+ that should be included or excluded from the test run.
+
+ :param node: AST Node corresponding to this Node.
+ """
+ ManifestItem.__init__(self, node)
+ self.child_map = {}
+
+ @classmethod
+ def create(cls):
+ """Create an empty IncludeManifest tree"""
+ node = DataNode(None)
+ return cls(node)
+
+ def append(self, child):
+ ManifestItem.append(self, child)
+ self.child_map[child.name] = child
+ assert len(self.child_map) == len(self.children)
+
+ def include(self, test):
+ """Return a boolean indicating whether a particular test should be
+ included in a test run, based on the IncludeManifest tree rooted on
+ this object.
+
+ :param test: The test object"""
+ path_components = self._get_components(test.url)
+ return self._include(test, path_components)
+
+ def _include(self, test, path_components):
+ if path_components:
+ next_path_part = path_components.pop()
+ if next_path_part in self.child_map:
+ return self.child_map[next_path_part]._include(test, path_components)
+
+ node = self
+ while node:
+ try:
+ skip_value = self.get("skip", {"test_type": test.item_type}).lower()
+ assert skip_value in ("true", "false")
+ return skip_value != "true"
+ except KeyError:
+ if node.parent is not None:
+ node = node.parent
+ else:
+ # Include by default
+ return True
+
+ def _get_components(self, url):
+ rv = []
+ url_parts = urlparse.urlsplit(url)
+ variant = ""
+ if url_parts.query:
+ variant += "?" + url_parts.query
+ if url_parts.fragment:
+ variant += "#" + url_parts.fragment
+ if variant:
+ rv.append(variant)
+ rv.extend([item for item in reversed(url_parts.path.split("/")) if item])
+ return rv
+
+ def _add_rule(self, test_manifests, url, direction):
+ maybe_path = os.path.join(os.path.abspath(os.curdir), url)
+ rest, last = os.path.split(maybe_path)
+ variant = ""
+ if "#" in last:
+ last, fragment = last.rsplit("#", 1)
+ variant += "#" + fragment
+ if "?" in last:
+ last, query = last.rsplit("?", 1)
+ variant += "?" + query
+
+ maybe_path = os.path.join(rest, last)
+ paths = glob.glob(maybe_path)
+
+ if paths:
+ urls = []
+ for path in paths:
+ for manifest, data in test_manifests.iteritems():
+ rel_path = os.path.relpath(path, data["tests_path"])
+ if ".." not in rel_path.split(os.sep):
+ urls.append(data["url_base"] + rel_path.replace(os.path.sep, "/") + variant)
+ break
+ else:
+ urls = [url]
+
+ assert direction in ("include", "exclude")
+
+ for url in urls:
+ components = self._get_components(url)
+
+ node = self
+ while components:
+ component = components.pop()
+ if component not in node.child_map:
+ new_node = IncludeManifest(DataNode(component))
+ node.append(new_node)
+ new_node.set("skip", node.get("skip", {}))
+
+ node = node.child_map[component]
+
+ skip = False if direction == "include" else True
+ node.set("skip", str(skip))
+
+ def add_include(self, test_manifests, url_prefix):
+ """Add a rule indicating that tests under a url path
+ should be included in test runs
+
+ :param url_prefix: The url prefix to include
+ """
+ return self._add_rule(test_manifests, url_prefix, "include")
+
+ def add_exclude(self, test_manifests, url_prefix):
+ """Add a rule indicating that tests under a url path
+ should be excluded from test runs
+
+ :param url_prefix: The url prefix to exclude
+ """
+ return self._add_rule(test_manifests, url_prefix, "exclude")
+
+
+def get_manifest(manifest_path):
+ with open(manifest_path) as f:
+ return conditional.compile(f, data_cls_getter=lambda x, y: IncludeManifest)