Skip to content

Commit 4633417

Browse files
committed
"copy" operation should copy by value, not by reference, fixes stefankoegl#8
1 parent 3829275 commit 4633417

2 files changed

Lines changed: 13 additions & 1 deletion

File tree

jsonpatch.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -422,5 +422,5 @@ class CopyOperation(PatchOperation):
422422

423423
def apply(self, obj):
424424
subobj, part = self.locate(obj, self.location)
425-
value = subobj[part]
425+
value = copy.deepcopy(subobj[part])
426426
AddOperation(self.operation['to'], {'value': value}).apply(obj)

tests.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,18 @@ def test_copy_array_item(self):
8686
self.assertEqual(res, {'foo': ['all', 'grass', 'cows', 'grass', 'eat']})
8787

8888

89+
def test_copy_mutable(self):
90+
""" test if mutable objects (dicts and lists) are copied by value """
91+
obj = {'foo': [{'bar': 42}, {'baz': 3.14}], 'boo': []}
92+
# copy object somewhere
93+
res = jsonpatch.apply_patch(obj, [{'copy': '/foo/0', 'to': '/boo/0' }])
94+
self.assertEqual(res, {'foo': [{'bar': 42}, {'baz': 3.14}], 'boo': [{'bar': 42}]})
95+
# modify original object
96+
res = jsonpatch.apply_patch(res, [{'add': '/foo/0/zoo', 'value': 255}])
97+
# check if that didn't modify the copied object
98+
self.assertEqual(res['boo'], [{'bar': 42}])
99+
100+
89101
def test_test_success(self):
90102
obj = {'baz': 'qux', 'foo': ['a', 2, 'c']}
91103
jsonpatch.apply_patch(obj, [{'test': '/baz', 'value': 'qux'},

0 commit comments

Comments
 (0)