Example #1
0
class Test_Manifest_resolve(unittest.TestCase):

    def setUp(self):
        self.mfp = ManifestFileParser()

    def test_empty(self):
        m = Manifest()
        self.assertTrue(m.resolve("") is m)

    def test_single_entry(self):
        m = self.mfp.build(["foo"])
        self.assertTrue(m.resolve("") is m)
        self.assertTrue(m.resolve("foo") is m["foo"])

    def test_missing_is_None(self):
        m = self.mfp.build(["foo"])
        self.assertTrue(m.resolve("bar") is None)

    def test_grandchild(self):
        m = self.mfp.build(["foo", "\tbar"])
        self.assertTrue(m.resolve("") is m)
        self.assertTrue(m.resolve("foo") is m["foo"])
        self.assertTrue(m.resolve("foo/bar") is m["foo"]["bar"])

    def test_dot_path(self):
        m = self.mfp.build(["foo", "\tbar"])
        self.assertTrue(m.resolve("./foo") is m["foo"])
        self.assertTrue(m.resolve("foo/./") is m["foo"])
        self.assertTrue(m.resolve("foo/./bar") is m["foo"]["bar"])
        self.assertTrue(m.resolve("./foo/./bar/.") is m["foo"]["bar"])
        self.assertTrue(m.resolve("./foo/./bar/./") is m["foo"]["bar"])

    def test_dotdot_path(self):
        m = self.mfp.build(["foo", "\tbar"])
        self.assertTrue(m.resolve("foo/..") is m)
        self.assertTrue(m.resolve("foo/../foo") is m["foo"])
        self.assertTrue(m.resolve("foo/../foo/bar") is m["foo"]["bar"])
        self.assertTrue(m.resolve("./foo/./bar/..") is m["foo"])
        self.assertTrue(m.resolve("./foo/bar/../") is m["foo"])
        self.assertTrue(m.resolve("./foo/bar/../..") is m)

    def test_excessive_dotdot_fails(self):
        m = self.mfp.build(["foo", "\tbar"])
        self.assertTrue(m.resolve("..") is None)
        self.assertTrue(m.resolve("../") is None)
        self.assertTrue(m.resolve("foo/../..") is None)
        self.assertTrue(m.resolve("foo/bar/../../..") is None)
        self.assertTrue(m.resolve("foo/bar/../bar/../../..") is None)
class Test_Manifest_merge(unittest.TestCase):

    def setUp(self):
        self.mfp = ManifestFileParser(Manifest)

    def test_nothing(self):
        self.assertEqual(list(Manifest.merge()), [])

    def test_one_empty(self):
        m = Manifest()
        self.assertEqual(list(Manifest.merge(m)), [])

    def test_two_empties(self):
        m1, m2 = Manifest(), Manifest_from_walking_unpacked_tar("empty.tar")
        self.assertEqual(list(Manifest.merge(m1, m2)), [])

    def test_one_single_file(self):
        m = Manifest_from_walking_unpacked_tar("single_file.tar")
        self.assertEqual(list(Manifest.merge(m)), [("foo",)])

    def test_single_file_x2(self):
        m1 = Manifest_from_walking_unpacked_tar("single_file.tar")
        m2 = self.mfp.build(["foo"])
        self.assertEqual(list(Manifest.merge(m1, m2)), [("foo", "foo")])

    def test_three_different_singles(self):
        m1, m2, m3 = map(self.mfp.build, (["foo"], ["bar"], ["baz"]))
        self.assertEqual(list(Manifest.merge(m1, m2, m3)), [
            (None, "bar", None), (None, None, "baz"), ("foo", None, None)])

    def test_three_mixed_singles(self):
        m1, m2, m3 = map(self.mfp.build, (["foo"], ["bar"], ["foo"]))
        self.assertEqual(list(Manifest.merge(m1, m2, m3)), [
            (None, "bar", None), ("foo", None, "foo")])

    def test_three_with_overlap(self):
        ms = map(self.mfp.build,
                 (["foo", "same"], ["bar", "same"], ["baz", "same"]))
        self.assertEqual(list(Manifest.merge(*ms)), [
            (None, "bar", None), (None, None, "baz"), ("foo", None, None),
            ("same", "same", "same")])

    def test_empty_subdir_vs_nonepty_subdir(self):
        m1 = Manifest_from_walking_unpacked_tar("file_and_empty_subdir.tar")
        m2 = Manifest_from_walking_unpacked_tar("file_and_subdir.tar")
        self.assertEqual(list(Manifest.merge(m1, m2)), [
            ("file", "file"), ("subdir", "subdir"), (None, "subdir/foo")])

    def test_custom_key(self):
        m1 = self.mfp.build(["1foo", "2bar", "3baz"])
        m2 = self.mfp.build(["abc", "def", "ghi"])
        m3 = self.mfp.build(["123", "456", "789"])
        self.assertEqual(
            list(Manifest.merge(m1, m2, m3, key = lambda px: True)), [
                ("1foo", "abc", "123"),
                ("2bar", "def", "456"),
                ("3baz", "ghi", "789")])

    def test_nonrecursive(self):
        m1 = self.mfp.build(["bar", "foo", "  bar", "  foo"])
        m2 = self.mfp.build(["foo", "  foo", "xyzzy"])
        m3 = self.mfp.build(["foo", "  bar", "    baz", "  foo", "    foo"])
        self.assertEqual(list(Manifest.merge(m1, m2, m3)), [
            ("bar", None, None),
            ("foo", "foo", "foo"),
            ("foo/bar", None, "foo/bar"),
            (None, None, "foo/bar/baz"),
            ("foo/foo", "foo/foo", "foo/foo"),
            (None, None, "foo/foo/foo"),
            (None, "xyzzy", None)])

        # now without recursion
        self.assertEqual(list(Manifest.merge(m1, m2, m3, recursive = False)), [
            ("bar", None, None),
            ("foo", "foo", "foo"),
            (None, "xyzzy", None)])

        # and finally with selective recursion (only recurse into "foo"s)
        actual = []
        gen = Manifest.merge(m1, m2, m3, recursive = False)
        try:
            t = next(gen)
            while True:
                actual.append(t)
                paths = [p for p in t if p is not None]
                self.assertTrue(paths)
                path = paths[0]
                self.assertEqual([path] * len(paths), paths)
                try:
                    last_component = path.rsplit("/", 1)[1]
                except:
                    last_component = path
                if last_component == "foo":
                    t = gen.send(True)
                else:
                    t = next(gen)
        except StopIteration:
            pass

        self.assertEqual(actual, [
            ("bar", None, None),
            ("foo", "foo", "foo"),
            ("foo/bar", None, "foo/bar"),
            ("foo/foo", "foo/foo", "foo/foo"),
            (None, None, "foo/foo/foo"),
            (None, "xyzzy", None)])
class Test_ManifestFileParser_build(unittest.TestCase):

    def setUp(self):
        self.mfp = ManifestFileParser()

    def test_empty(self):
        m = self.mfp.build(StringIO(""))
        self.assertEqual(m, {})

    def test_single_word(self):
        m = self.mfp.build(StringIO("foo"))
        self.assertEqual(m, {"foo": {}})

    def test_two_words(self):
        m = self.mfp.build(StringIO("foo\nbar"))
        self.assertEqual(m, {"foo": {}, "bar": {}})

    def test_entry_with_child(self):
        m = self.mfp.build(StringIO("foo\n\tbar"))
        self.assertEqual(m, {"foo": {"bar": {}}})

    def test_entry_with_children(self):
        m = self.mfp.build(StringIO("foo\n\tbar\n\tbaz"))
        self.assertEqual(m, {"foo": {"bar": {}, "baz": {}}})

    def test_entry_with_child_and_sibling(self):
        m = self.mfp.build(StringIO("foo\n\tbar\nfooz"))
        self.assertEqual(m, {"foo": {"bar": {}}, "fooz": {}})

    def test_entry_with_grandchild(self):
        m = self.mfp.build(StringIO("foo\n\tbar\n\t\tbaz"))
        self.assertEqual(m, {"foo": {"bar": {"baz": {}}}})

    def test_entry_with_grandchild_and_sibling(self):
        m = self.mfp.build(StringIO("foo\n\tbar\n\t\tbaz\nxyzzy"))
        self.assertEqual(m, {"foo": {"bar": {"baz": {}}}, "xyzzy": {}})

    def test_parent_refs(self):
        m = self.mfp.build(StringIO("foo\n\tbar"))
        self.assertEqual(m, {"foo": {"bar": {}}})
        self.assertEqual(m.getparent(), None)
        self.assertEqual(m["foo"].getparent(), m)
        self.assertEqual(m["foo"]["bar"].getparent(), m["foo"])

    def test_empty_attrs(self):
        m = self.mfp.build(["foo {}"])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(), {})

    def test_unknown_attr(self):
        m = self.mfp.build(["foo {bar: baz}"])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(), { "bar": "baz"})

    def test_size_attr(self):
        m = self.mfp.build(["foo {size: 1}"])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(), {"size": 1})

    def test_invalid_size_attr_raises(self):
        self.assertRaises(ValueError, self.mfp.build, ["foo {size: bar}"])
        self.assertRaises(ValueError, self.mfp.build, ["foo {size: -1}"])

    def test_two_attrs(self):
        sha1 = "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef"
        m = self.mfp.build(["foo {size: 1, sha1: %s}" % (sha1)])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(), {"size": 1, "sha1": sha1})

    def test_sha1_attr_lowered(self):
        sha1 = "deadbeefDEADBEEFdeadbeefdeadbeefdeadbeef"
        m = self.mfp.build(["foo {size: 1, sha1: %s}" % (sha1)])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(), {"size": 1, "sha1": sha1.lower()})

    def test_invalid_sha1_attr_raises(self):
        self.assertRaises(ValueError, self.mfp.build, ["foo {sha1: not_hex}"])
        self.assertRaises(ValueError, self.mfp.build, ["foo {sha1: 123}"]) # <40

    def test_mode_Xid_attr(self):
        m = self.mfp.build(["foo { mode: 0o100644, uid: 1000, gid: 100 }"])
        self.assertEqual(m, {"foo": {}})
        self.assertEqual(m["foo"].getattrs(),
                         {"mode": 0o100644, "uid": 1000, "gid": 100})

    def test_invalid_mode_Xid_attr_raises(self):
        self.assertRaises(ValueError, self.mfp.build, ["foo {mode: not_int}"])
        self.assertRaises(ValueError, self.mfp.build, ["foo {uid: -13}"])
        self.assertRaises(ValueError, self.mfp.build, ["foo {gid: 0x123foo}"])