Test_30_update_with_merge.assert_dicts_equal()   B
last analyzed

Complexity

Conditions 6

Size

Total Lines 9

Duplication

Lines 8
Ratio 88.89 %

Importance

Changes 0
Metric Value
cc 6
dl 8
loc 9
rs 8.6666
c 0
b 0
f 0
1
#
2
# Forked from m9dicts.tests.{api,dicts}
3
#
4
# Copyright (C) 2011 - 2016 Satoru SATOH <ssato @ redhat.com>
5
# Copyright (C) 2017, 2018 Red Hat, Inc.
6
#
7
# pylint: disable=missing-docstring,invalid-name,protected-access
8
# pylint: disable=ungrouped-imports
9
from __future__ import absolute_import
10
11
import copy
12
import unittest
13
import anyconfig.dicts as TT
14
15
from tests.common import dicts_equal
16
from anyconfig.compat import OrderedDict
17
from anyconfig.utils import is_dict_like
18
19
20
class Test_10_get(unittest.TestCase):
21
22
    def test_10_empty_path(self):
23
        dic = dict(a=1, b=[1, 2])
24
        (dic2, err) = TT.get(dic, '')
25
        self.assertEqual(err, '')
26
        self.assertTrue(dicts_equal(dic2, dic))
27
28
    def test_20_json_pointer(self):
29
        # test case in rfc, http://tools.ietf.org/html/rfc6901
30
        dic = {"foo": ["bar", "baz"],
31
               "": 0,
32
               "a/b": 1,
33
               "c%d": 2,
34
               "e^f": 3,
35
               "g|h": 4,
36
               r"i\\j": 5,
37
               r'k\"l': 6,
38
               " ": 7,
39
               "m~n": 8}
40
41
        self.assertTrue(dicts_equal(TT.get(dic, "")[0], dic))
42
        self.assertEqual(TT.get(dic, "/foo")[0], ["bar", "baz"])
43
        self.assertEqual(TT.get(dic, "/foo/0")[0], "bar")
44
        self.assertEqual(TT.get(dic, "/")[0], 0)
45
        self.assertEqual(TT.get(dic, "/a~1b")[0], 1)
46
        self.assertEqual(TT.get(dic, "/c%d")[0], 2)
47
        self.assertEqual(TT.get(dic, "/e^f")[0], 3)
48
        self.assertEqual(TT.get(dic, "/g|h")[0], 4)
49
        self.assertEqual(TT.get(dic, r"/i\\j")[0], 5)
50
        self.assertEqual(TT.get(dic, r'/k\"l')[0], 6)
51
        self.assertEqual(TT.get(dic, "/ ")[0], 7)
52
        self.assertEqual(TT.get(dic, "/m~0n")[0], 8)
53
54
    def test_22_json_pointer__array(self):
55
        dic = dict(a=[1, 2], )
56
        self.assertEqual(TT.get(dic, "/a/1"), (2, ''))
57
58
        (val, msg) = TT.get(dic, "/a/2")
59
        self.assertTrue(val is None)
60
        self.assertTrue(bool(msg))
61
        # maybe the error message depends on python version.
62
        # self.assertEqual(msg, 'list index out of range')
63
64
        (val, msg) = TT.get(dic, "/a/b/d/-")
65
        self.assertTrue(val is None)
66
        self.assertTrue(bool(msg))
67
        # Likewise.
68
        # self.assertEqual(msg, 'list indices must be integers...')
69
70
71
class Test_10_update_with_replace(unittest.TestCase):
72
73
    ac_merge = TT.MS_REPLACE
74
75
    dic = OrderedDict((("a", 1), ("b", [1, 3]), ("c", "abc"), ("f", None)))
76
    other = OrderedDict((("a", 2), ("b", [0, 1]),
77
                         ("c", OrderedDict((("d", "d"), ("e", 1)))),
78
                         ("d", "d")))
79
80
    def assert_dicts_equal(self, dic, upd, ref):
81
        if not is_dict_like(upd):
82
            upd = OrderedDict(upd)
83
84
        self.assertTrue(all(dic[k] == upd[k] for k in upd.keys()))
85
        self.assertTrue(all(dic[k] == ref[k] for k in ref.keys()
86
                            if k not in upd))
87
88
    def assert_updated(self, other):
89
        dic = copy.deepcopy(self.dic)
90
        TT.merge(dic, other, ac_merge=self.ac_merge)
91
        self.assert_dicts_equal(dic, other, self.dic)
92
93
    def test_10_update_with_a_odict(self):
94
        self.assert_updated(self.other)
95
96
    def test_12_update_with_a_dict(self):
97
        self.assert_updated(dict(self.other))
98
99
    def test_20_update_with_iterable(self):
100
        self.assert_updated(self.other.items())
101
102
    def test_30_update_with_invalid(self):
103
        try:
104
            raised = False
105
            TT.merge(self.dic, 1)
106
        except (ValueError, TypeError):
107
            raised = True
108
109
        self.assertTrue(raised)
110
111
112
class Test_20_update_wo_replace(Test_10_update_with_replace):
113
114
    ac_merge = TT.MS_NO_REPLACE
115
116
    def assert_dicts_equal(self, dic, upd, ref):
117
        if not is_dict_like(upd):
118
            upd = OrderedDict(upd)
119
120
        self.assertTrue(all(dic[k] == upd[k] for k in upd.keys()
121
                            if k not in ref))
122
        self.assertTrue(all(dic[k] == ref[k] for k in ref.keys()))
123
124
125
class Test_30_update_with_merge(Test_10_update_with_replace):
126
127
    ac_merge = TT.MS_DICTS
128
    replaced_keys = "a b d".split()
129 View Code Duplication
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
130
    def assert_dicts_equal(self, dic, upd, ref):
131
        if not is_dict_like(upd):
132
            upd = OrderedDict(upd)
133
134
        self.assertTrue(all(dic[k] == upd[k] for k in self.replaced_keys))
135
        self.assertTrue(all(dic["c"][k] == upd["c"][k] for k
136
                            in upd["c"].keys()))
137
        self.assertTrue(all(dic[k] == ref[k] for k in ref.keys()
138
                            if k not in upd))
139
140
141
class Test_32_update_with_merge_lists(Test_10_update_with_replace):
142
143
    ac_merge = TT.MS_DICTS_AND_LISTS
144 View Code Duplication
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
145
    def assert_dicts_equal(self, dic, upd, ref):
146
        if not is_dict_like(upd):
147
            upd = OrderedDict(upd)
148
149
        self.assertTrue(all(dic[k] == upd[k] for k in ["d"]))
150
        self.assertEqual(dic["c"], upd["c"])  # Overwritten.
151
        self.assertTrue(all(dic[k] == ref[k] for k in ref.keys()
152
                            if k not in upd))
153
154
155
class Test_40_merge(unittest.TestCase):
156
157
    dic = dict(a=1, b=dict(b=[0, 1], c="C"), name="a")
158
    upd = dict(a=2, b=dict(b=[1, 2, 3, 4, 5], d="D"), e="E")
159
160
    def test_10_update_with_replace(self):
161
        dic = copy.deepcopy(self.dic)
162
        exp = copy.deepcopy(self.upd)
163
        exp["name"] = dic["name"]
164
165
        TT.merge(dic, self.upd, ac_merge=TT.MS_REPLACE)
166
        self.assertTrue(dicts_equal(dic, exp))
167
168
    def test_20_update_wo_replace(self):
169
        dic = copy.deepcopy(self.dic)
170
        exp = copy.deepcopy(self.dic)
171
        exp["e"] = self.upd["e"]
172
173
        TT.merge(dic, self.upd, ac_merge=TT.MS_NO_REPLACE)
174
        self.assertTrue(dicts_equal(dic, exp))
175
176
    def test_30_update_with_merge(self):
177
        dic = copy.deepcopy(self.dic)
178
        exp = copy.deepcopy(self.upd)
179
        exp["b"]["c"] = dic["b"]["c"]
180
        exp["name"] = dic["name"]
181
182
        TT.merge(dic, self.upd, ac_merge=TT.MS_DICTS)
183
        self.assertTrue(dicts_equal(dic, exp))
184 View Code Duplication
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
185
    def test_40_update_with_merge_lists(self):
186
        dic = copy.deepcopy(self.dic)
187
        exp = copy.deepcopy(self.upd)
188
        exp["b"]["b"] = [0] + exp["b"]["b"]
189
        exp["b"]["c"] = dic["b"]["c"]
190
        exp["name"] = dic["name"]
191
192
        TT.merge(dic, self.upd, ac_merge=TT.MS_DICTS_AND_LISTS)
193
        self.assertTrue(dicts_equal(dic, exp))
194
195
    def test_50_update_with_custom_merge(self):
196
        def set_none_merge_strat(self, other, key, *args, **kwargs):
197
            for k in self:
198
                self[k] = None
199
200
        dic = copy.deepcopy(self.dic)
201
        exp = dict(zip(dic.keys(), [None for _ in dic]))
202
203
        TT.merge(dic, self.upd, ac_merge=set_none_merge_strat)
204
        self.assertTrue(dicts_equal(dic, exp))
205
206
# vim:sw=4:ts=4:et:
207