Esempio n. 1
0
    def test_popitem(self):
        the_list = [("a", 1), ("b", 2), ("a", 3)]

        # Removes the last item
        old = OrderedMultiDict(the_list)
        self.assertTupleEqual(old.popitem(), ("a", 3))
        self.assertEqual(len(old), 2)
        self.assertTupleEqual(old.popitem(), ("b", 2))
        self.assertEqual(len(old), 1)
        self.assertTupleEqual(old.popitem(), ("a", 1))
        self.assertEqual(len(old), 0)
        self.assertRaises(KeyError, old.popitem)

        try:
            from pvl.collections import PVLMultiDict

            # Removes a random item, in proper dict-like fashion
            new = PVLMultiDict(the_list)
            self.assertIn(new.popitem(), the_list)
            self.assertEqual(len(new), 2)
            new.popitem()
            new.popitem()
            self.assertRaises(KeyError, new.popitem)
        except ImportError:
            pass
Esempio n. 2
0
    def test_discard(self):
        the_list = [("a", 1), ("b", 2), ("a", 3)]

        # Has a set-like .discard() function
        old = OrderedMultiDict(the_list)
        old.discard("a")
        self.assertEqual(len(old), 1)
        self.assertRaises(KeyError, old.getall, "a")
        self.assertRaises(KeyError, old.__getitem__, "a")

        self.assertEqual(old.__getitem__("b"), 2)
        old.discard("b")
        self.assertEqual(len(old), 0)
        self.assertRaises(KeyError, old.__getitem__, "b")

        old.discard("c")
        self.assertEqual(len(old), 0)

        try:
            from pvl.collections import PVLMultiDict

            # Does not have a set-like .discard() function,
            # because it isn't a set!
            new = PVLMultiDict(the_list)
            self.assertRaises(AttributeError, getattr, new, "discard")
        except ImportError:
            pass
Esempio n. 3
0
    def test_repr(self):
        # Original repr
        old = OrderedMultiDict()
        self.assertEqual(repr(old), 'OrderedMultiDict([])')

        try:
            from pvl.collections import PVLMultiDict
            # MultiDict repr
            new = PVLMultiDict()
            self.assertEqual(repr(new), 'PVLMultiDict()')
        except ImportError:
            pass
Esempio n. 4
0
    def test_py3_items(self):
        the_list = [("a", 1), ("b", 2), ("a", 3)]

        # These views are returned as lists!
        old = OrderedMultiDict(the_list)
        self.assertIsInstance(old.items(), pvl.collections.ItemsView)
        self.assertIsInstance(old.keys(), pvl.collections.KeysView)
        self.assertIsInstance(old.values(), pvl.collections.ValuesView)
        views = [
            (old.items(), old.keys(), old.values()),
        ]

        try:
            from pvl.collections import PVLMultiDict

            # These are proper Python 3 views:
            new = PVLMultiDict(the_list)
            self.assertIsInstance(new.items(), abc.ItemsView)
            self.assertIsInstance(new.keys(), abc.KeysView)
            self.assertIsInstance(new.values(), abc.ValuesView)
            views.append(
                (list(new.items()), list(new.keys()), list(new.values())))
        except ImportError:
            pass

        # However, if you wrap the new items in a list (as above), this is
        # the same:
        for items, keys, values in views:
            self.assertTupleEqual(items[0], ("a", 1))
            self.assertTupleEqual(items[1], ("b", 2))
            self.assertTupleEqual(items[2], ("a", 3))
            self.assertEqual(items.index(("a", 1)), 0)
            self.assertEqual(items.index(("b", 2)), 1)
            self.assertEqual(items.index(("a", 3)), 2)

            self.assertEqual(keys[0], "a")
            self.assertEqual(keys[1], "b")
            self.assertEqual(keys[2], "a")
            self.assertEqual(keys.index("a"), 0)
            self.assertEqual(keys.index("b"), 1)

            self.assertEqual(values[0], 1)
            self.assertEqual(values[1], 2)
            self.assertEqual(values[2], 3)
            self.assertEqual(values.index(1), 0)
            self.assertEqual(values.index(2), 1)
            self.assertEqual(values.index(3), 2)
Esempio n. 5
0
    def test_as_list(self):
        the_list = [('a', 1), ('b', 2)]

        # Returns list of tuples:
        old = OrderedMultiDict(the_list)
        self.assertListEqual(list(old), [('a', 1), ('b', 2)])

        try:
            from pvl.collections import PVLMultiDict
            # Returns list of keys, which is semantically identical to calling
            # list() on a dict.
            new = PVLMultiDict(the_list)
            self.assertListEqual(list(new), ['a', 'b'])
        except ImportError:
            pass
Esempio n. 6
0
    def test_pop(self):
        the_list = [("a", 1), ("b", 2), ("a", 3)]

        # Removes all keys that match, but returns only the first value, which
        # is weird
        old = OrderedMultiDict(the_list)
        self.assertEqual(old.pop("a"), 1)
        self.assertEqual(len(old), 1)
        self.assertRaises(KeyError, old.getall, "a")
        self.assertRaises(KeyError, old.pop, "a")
        self.assertEqual(old.pop("a", 42), 42)

        self.assertEqual(old.pop("b"), 2)
        self.assertEqual(len(old), 0)
        self.assertRaises(KeyError, old.pop, "b")
        self.assertRaises(KeyError, old.__getitem__, "b")

        self.assertRaises(KeyError, old.pop, "c")
        self.assertEqual(old.pop("c", 42), 42)

        try:
            from pvl.collections import PVLMultiDict

            # Removes only the first key
            new = PVLMultiDict(the_list)
            self.assertEqual(new.pop("a"), 1)
            self.assertEqual(len(new), 2)
            self.assertListEqual(new.getall("a"), [
                3,
            ])
            self.assertEqual(new.pop("a"), 3)
            self.assertEqual(new.pop("a", 42), 42)

            self.assertEqual(new.pop("b"), 2)
            self.assertEqual(len(new), 0)
            self.assertRaises(KeyError, new.pop, "b")
            self.assertRaises(KeyError, new.__getitem__, "b")

            self.assertRaises(KeyError, new.pop, "c")
            self.assertEqual(new.pop("c", 42), 42)
        except ImportError:
            pass
Esempio n. 7
0
    def test_conversion(self):
        the_list = [("a", 1), ("b", 2), ("a", 3)]

        # This returns a list of key, value tuple pairs
        old = OrderedMultiDict(the_list)
        self.assertListEqual(list(old), the_list)

        # === Callling dict(old) ===
        # This is the one test that I could not get to pass from
        # pvl 0.3, and now I know why: it is because the
        # OrderedMultiDict inherently carries two copies of the
        # information added to it: one in the default dict that
        # it inherits from being directly subclassed from dict,
        # and the other is an internal list of key, value tuples.
        #
        # When I tried to run this test using the regular Python
        # interpreters, I got
        # self.assertEqual(dict(old), {'a': 1, 'b': 2})
        # This is because when it is passed to the dict constructor,
        # Python makes it into a regular Mapping object with unique
        # keys, inevitably loosing the double value of 'a'.
        #
        # I could not understand why pvl 0.3 had this test that it
        # expected to pass:
        # expected_dict = {
        #     'a': [1, 3],
        #     'b': [2],
        # }
        #
        # That was until Travis ran the tests using both the regular
        # python interpreter and pypy (I don't usually run pypy tests locally).
        # If you run the test with a regular python interpreter, you get the
        # first result, with the second value of 'a' being lost.  If you run
        # the test with the pypy3 interpreter, you get the second result, with
        # the values for the keys being lists!
        #
        # This scared the heck out of me.
        #
        # This is what I think is happening:
        # When you run dict() on an OrderedMultiDict, the python interpreter
        # uses the fact that it is a Mapping item, and internally runs its
        # .items() function to get the (key, value) pairs and builds a new
        # dict from them (it encounters a second value for the key 'a', and
        # looses it).  The pypy3 interpreter, must not use the .items()
        # function on the passed-in Mapping object, but notices that this
        # object derives from a dict, and so just grabs the internal dict
        # representation, which OrderedMultiDict hides from the user, but
        # is implemented as single keys with lists as the values.
        #
        # And that's why the same code produces different results with
        # different interpreters.

        try:
            from pvl.collections import PVLMultiDict

            # This returns the same thing that calling list() on a dict would,
            # the list of keys
            new = PVLMultiDict(the_list)
            self.assertListEqual(list(new), ["a", "b", "a"])
            self.assertEqual(dict(new), {"a": 1, "b": 2})
        except ImportError:
            pass