Source code

Revision control

Other Tools

Test Info:

#!/usr/bin/env python
# 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/.
from __future__ import absolute_import
import os
import shutil
import tempfile
import unittest
from six import StringIO
import mozunit
from manifestparser import ManifestParser
here = os.path.dirname(os.path.abspath(__file__))
class TestManifestParser(unittest.TestCase):
"""
Test the manifest parser
You must have manifestparser installed before running these tests.
Run ``python manifestparser.py setup develop`` with setuptools installed.
"""
def test_sanity(self):
"""Ensure basic parser is sane"""
parser = ManifestParser()
mozmill_example = os.path.join(here, "mozmill-example.ini")
parser.read(mozmill_example)
tests = parser.tests
self.assertEqual(
len(tests), len(open(mozmill_example).read().strip().splitlines())
)
# Ensure that capitalization and order aren't an issue:
lines = ["[%s]" % test["name"] for test in tests]
self.assertEqual(lines, open(mozmill_example).read().strip().splitlines())
# Show how you select subsets of tests:
mozmill_restart_example = os.path.join(here, "mozmill-restart-example.ini")
parser.read(mozmill_restart_example)
restart_tests = parser.get(type="restart")
self.assertTrue(len(restart_tests) < len(parser.tests))
self.assertEqual(
len(restart_tests), len(parser.get(manifest=mozmill_restart_example))
)
self.assertFalse(
[
test
for test in restart_tests
if test["manifest"] != os.path.join(here, "mozmill-restart-example.ini")
]
)
self.assertEqual(
parser.get("name", tags=["foo"]),
[
"restartTests/testExtensionInstallUninstall/test2.js",
"restartTests/testExtensionInstallUninstall/test1.js",
],
)
self.assertEqual(
parser.get("name", foo="bar"),
["restartTests/testExtensionInstallUninstall/test2.js"],
)
def test_include(self):
"""Illustrate how include works"""
include_example = os.path.join(here, "include-example.ini")
parser = ManifestParser(manifests=(include_example,))
# All of the tests should be included, in order:
self.assertEqual(parser.get("name"), ["crash-handling", "fleem", "flowers"])
self.assertEqual(
[
(test["name"], os.path.basename(test["manifest"]))
for test in parser.tests
],
[
("crash-handling", "bar.ini"),
("fleem", "include-example.ini"),
("flowers", "foo.ini"),
],
)
# The including manifest is always reported as a part of the generated test object.
self.assertTrue(
all(
[
t["ancestor_manifest"] == "include-example.ini"
for t in parser.tests
if t["name"] != "fleem"
]
)
)
# The manifests should be there too:
self.assertEqual(len(parser.manifests()), 3)
# We already have the root directory:
self.assertEqual(here, parser.rootdir)
# DEFAULT values should persist across includes, unless they're
# overwritten. In this example, include-example.ini sets foo=bar, but
# it's overridden to fleem in bar.ini
self.assertEqual(parser.get("name", foo="bar"), ["fleem", "flowers"])
self.assertEqual(parser.get("name", foo="fleem"), ["crash-handling"])
# Passing parameters in the include section allows defining variables in
# the submodule scope:
self.assertEqual(parser.get("name", tags=["red"]), ["flowers"])
# However, this should be overridable from the DEFAULT section in the
# included file and that overridable via the key directly connected to
# the test:
self.assertEqual(parser.get(name="flowers")[0]["blue"], "ocean")
self.assertEqual(parser.get(name="flowers")[0]["yellow"], "submarine")
# You can query multiple times if you need to:
flowers = parser.get(foo="bar")
self.assertEqual(len(flowers), 2)
# Using the inverse flag should invert the set of tests returned:
self.assertEqual(
parser.get("name", inverse=True, tags=["red"]), ["crash-handling", "fleem"]
)
# All of the included tests actually exist:
self.assertEqual([i["name"] for i in parser.missing()], [])
# Write the output to a manifest:
buffer = StringIO()
parser.write(fp=buffer, global_kwargs={"foo": "bar"})
expected_output = """[DEFAULT]
foo = bar
[fleem]
[include/flowers]
blue = ocean
red = roses
yellow = submarine""" # noqa
self.assertEqual(buffer.getvalue().strip(), expected_output)
def test_include_manifest_defaults(self):
"""
Test that manifest_defaults and manifests() are correctly populated
when includes are used.
"""
include_example = os.path.join(here, "include-example.ini")
noinclude_example = os.path.join(here, "just-defaults.ini")
bar_path = os.path.join(here, "include", "bar.ini")
foo_path = os.path.join(here, "include", "foo.ini")
parser = ManifestParser(
manifests=(include_example, noinclude_example), rootdir=here
)
# Standalone manifests must be appear as-is.
self.assertTrue(include_example in parser.manifest_defaults)
self.assertTrue(noinclude_example in parser.manifest_defaults)
# Included manifests must only appear together with the parent manifest
# that included the manifest.
self.assertFalse(bar_path in parser.manifest_defaults)
self.assertFalse(foo_path in parser.manifest_defaults)
ancestor_ini = os.path.relpath(include_example, parser.rootdir)
self.assertTrue((ancestor_ini, bar_path) in parser.manifest_defaults)
self.assertTrue((ancestor_ini, foo_path) in parser.manifest_defaults)
# manifests() must only return file paths (strings).
manifests = parser.manifests()
self.assertEqual(len(manifests), 4)
self.assertIn(foo_path, manifests)
self.assertIn(bar_path, manifests)
self.assertIn(include_example, manifests)
self.assertIn(noinclude_example, manifests)
def test_include_handle_defaults_False(self):
"""
Test that manifest_defaults and manifests() are correct even when
handle_defaults is set to False.
"""
manifest = os.path.join(here, "include-example.ini")
foo_path = os.path.join(here, "include", "foo.ini")
parser = ManifestParser(
manifests=(manifest,), handle_defaults=False, rootdir=here
)
ancestor_ini = os.path.relpath(manifest, parser.rootdir)
self.assertIn(manifest, parser.manifest_defaults)
self.assertNotIn(foo_path, parser.manifest_defaults)
self.assertIn((ancestor_ini, foo_path), parser.manifest_defaults)
self.assertEqual(
parser.manifest_defaults[manifest],
{
"foo": "bar",
"here": here,
},
)
self.assertEqual(
parser.manifest_defaults[(ancestor_ini, foo_path)],
{
"here": os.path.join(here, "include"),
"red": "roses",
"blue": "ocean",
"yellow": "daffodils",
},
)
def test_include_repeated(self):
"""
Test that repeatedly included manifests are independent of each other.
"""
include_example = os.path.join(here, "include-example.ini")
included_foo = os.path.join(here, "include", "foo.ini")
# In the expected output, blue and yellow have the values from foo.ini
# (ocean, submarine) instead of the ones from include-example.ini
# (violets, daffodils), because the defaults in the included file take
# precedence over the values from the parent.
include_output = """[include/crash-handling]
foo = fleem
[fleem]
foo = bar
[include/flowers]
blue = ocean
foo = bar
red = roses
yellow = submarine
"""
included_output = """[include/flowers]
blue = ocean
yellow = submarine
"""
parser = ManifestParser(manifests=(include_example, included_foo), rootdir=here)
self.assertEqual(
parser.get("name"), ["crash-handling", "fleem", "flowers", "flowers"]
)
self.assertEqual(
[
(test["name"], os.path.basename(test["manifest"]))
for test in parser.tests
],
[
("crash-handling", "bar.ini"),
("fleem", "include-example.ini"),
("flowers", "foo.ini"),
("flowers", "foo.ini"),
],
)
self.check_included_repeat(
parser,
parser.tests[3],
parser.tests[2],
"%s%s" % (include_output, included_output),
)
# Same tests, but with the load order of the manifests swapped.
parser = ManifestParser(manifests=(included_foo, include_example), rootdir=here)
self.assertEqual(
parser.get("name"), ["flowers", "crash-handling", "fleem", "flowers"]
)
self.assertEqual(
[
(test["name"], os.path.basename(test["manifest"]))
for test in parser.tests
],
[
("flowers", "foo.ini"),
("crash-handling", "bar.ini"),
("fleem", "include-example.ini"),
("flowers", "foo.ini"),
],
)
self.check_included_repeat(
parser,
parser.tests[0],
parser.tests[3],
"%s%s" % (included_output, include_output),
)
def check_included_repeat(
self, parser, isolated_test, included_test, expected_output
):
include_example = os.path.join(here, "include-example.ini")
included_foo = os.path.join(here, "include", "foo.ini")
ancestor_ini = os.path.relpath(include_example, parser.rootdir)
manifest_default_key = (ancestor_ini, included_foo)
self.assertFalse("ancestor_manifest" in isolated_test)
self.assertEqual(included_test["ancestor_manifest"], "include-example.ini")
self.assertTrue(include_example in parser.manifest_defaults)
self.assertTrue(included_foo in parser.manifest_defaults)
self.assertTrue(manifest_default_key in parser.manifest_defaults)
self.assertEqual(
parser.manifest_defaults[manifest_default_key],
{
"foo": "bar",
"here": os.path.join(here, "include"),
"red": "roses",
"blue": "ocean",
"yellow": "daffodils",
},
)
buffer = StringIO()
parser.write(fp=buffer)
self.assertEqual(buffer.getvalue(), expected_output)
def test_invalid_path(self):
"""
Test invalid path should not throw when not strict
"""
manifest = os.path.join(here, "include-invalid.ini")
ManifestParser(manifests=(manifest,), strict=False)
def test_copy(self):
"""Test our ability to copy a set of manifests"""
tempdir = tempfile.mkdtemp()
include_example = os.path.join(here, "include-example.ini")
manifest = ManifestParser(manifests=(include_example,))
manifest.copy(tempdir)
self.assertEqual(
sorted(os.listdir(tempdir)), ["fleem", "include", "include-example.ini"]
)
self.assertEqual(
sorted(os.listdir(os.path.join(tempdir, "include"))),
["bar.ini", "crash-handling", "flowers", "foo.ini"],
)
from_manifest = ManifestParser(manifests=(include_example,))
to_manifest = os.path.join(tempdir, "include-example.ini")
to_manifest = ManifestParser(manifests=(to_manifest,))
self.assertEqual(to_manifest.get("name"), from_manifest.get("name"))
shutil.rmtree(tempdir)
def test_path_override(self):
"""You can override the path in the section too.
This shows that you can use a relative path"""
path_example = os.path.join(here, "path-example.ini")
manifest = ManifestParser(manifests=(path_example,))
self.assertEqual(manifest.tests[0]["path"], os.path.join(here, "fleem"))
def test_relative_path(self):
"""
Relative test paths are correctly calculated.
"""
relative_path = os.path.join(here, "relative-path.ini")
manifest = ManifestParser(manifests=(relative_path,))
self.assertEqual(
manifest.tests[0]["path"], os.path.join(os.path.dirname(here), "fleem")
)
self.assertEqual(manifest.tests[0]["relpath"], os.path.join("..", "fleem"))
self.assertEqual(
manifest.tests[1]["relpath"], os.path.join("..", "testsSIBLING", "example")
)
def test_path_from_fd(self):
"""
Test paths are left untouched when manifest is a file-like object.
"""
fp = StringIO("[section]\npath=fleem")
manifest = ManifestParser(manifests=(fp,))
self.assertEqual(manifest.tests[0]["path"], "fleem")
self.assertEqual(manifest.tests[0]["relpath"], "fleem")
self.assertEqual(manifest.tests[0]["manifest"], None)
def test_comments(self):
"""
ensure comments work, see
"""
comment_example = os.path.join(here, "comment-example.ini")
manifest = ManifestParser(manifests=(comment_example,))
self.assertEqual(len(manifest.tests), 8)
names = [i["name"] for i in manifest.tests]
self.assertFalse("test_0202_app_launch_apply_update_dirlocked.js" in names)
def test_verifyDirectory(self):
directory = os.path.join(here, "verifyDirectory")
# correct manifest
manifest_path = os.path.join(directory, "verifyDirectory.ini")
manifest = ManifestParser(manifests=(manifest_path,))
missing = manifest.verifyDirectory(directory, extensions=(".js",))
self.assertEqual(missing, (set(), set()))
# manifest is missing test_1.js
test_1 = os.path.join(directory, "test_1.js")
manifest_path = os.path.join(directory, "verifyDirectory_incomplete.ini")
manifest = ManifestParser(manifests=(manifest_path,))
missing = manifest.verifyDirectory(directory, extensions=(".js",))
self.assertEqual(missing, (set(), set([test_1])))
# filesystem is missing test_notappearinginthisfilm.js
missing_test = os.path.join(directory, "test_notappearinginthisfilm.js")
manifest_path = os.path.join(directory, "verifyDirectory_toocomplete.ini")
manifest = ManifestParser(manifests=(manifest_path,))
missing = manifest.verifyDirectory(directory, extensions=(".js",))
self.assertEqual(missing, (set([missing_test]), set()))
def test_just_defaults(self):
"""Ensure a manifest with just a DEFAULT section exposes that data."""
parser = ManifestParser()
manifest = os.path.join(here, "just-defaults.ini")
parser.read(manifest)
self.assertEqual(len(parser.tests), 0)
self.assertTrue(manifest in parser.manifest_defaults)
self.assertEquals(parser.manifest_defaults[manifest]["foo"], "bar")
def test_manifest_list(self):
"""
Ensure a manifest with just a DEFAULT section still returns
itself from the manifests() method.
"""
parser = ManifestParser()
manifest = os.path.join(here, "no-tests.ini")
parser.read(manifest)
self.assertEqual(len(parser.tests), 0)
self.assertTrue(len(parser.manifests()) == 1)
if __name__ == "__main__":
mozunit.main()