Fix failure of parameter overwrites in some cases
Some overwrites would fail raising a type mismatch error. See the
test: test_complex_overwrites_1 in test_parameters for one such case
diff --git a/reclass/datatypes/parameters.py b/reclass/datatypes/parameters.py
index c96a67d..cbee11f 100644
--- a/reclass/datatypes/parameters.py
+++ b/reclass/datatypes/parameters.py
@@ -153,6 +153,9 @@
ret = cur
for (key, newvalue) in iteritems(new):
if key.startswith(self._settings.dict_key_override_prefix) and not self._keep_overrides:
+ if not isinstance(newvalue, Value):
+ newvalue = Value(newvalue, self._settings, self._uri)
+ newvalue.overwrite = True
ret[key.lstrip(self._settings.dict_key_override_prefix)] = newvalue
else:
ret[key] = self._merge_recurse(ret.get(key), newvalue, path.new_subpath(key))
@@ -177,7 +180,6 @@
"""
-
if cur is None:
return new
elif isinstance(new, dict) and isinstance(cur, dict):
diff --git a/reclass/datatypes/tests/test_parameters.py b/reclass/datatypes/tests/test_parameters.py
index b5dc243..ecd112c 100644
--- a/reclass/datatypes/tests/test_parameters.py
+++ b/reclass/datatypes/tests/test_parameters.py
@@ -643,5 +643,18 @@
p1.interpolate()
self.assertEqual(p1.as_dict(), r)
+ def test_complex_overwrites_1(self):
+ # find a better name for this test
+ p1 = Parameters({ 'test': { 'dict': { 'a': '${values:one}', 'b': '${values:two}' } },
+ 'values': { 'one': 1, 'two': 2, 'three': { 'x': 'X', 'y': 'Y' } } }, SETTINGS, '')
+ p2 = Parameters({ 'test': { 'dict': { 'c': '${values:two}' } } }, SETTINGS, '')
+ p3 = Parameters({ 'test': { 'dict': { '~b': '${values:three}' } } }, SETTINGS, '')
+ r = {'test': {'dict': {'a': 1, 'b': {'x': 'X', 'y': 'Y'}, 'c': 2}}, 'values': {'one': 1, 'three': {'x': 'X', 'y': 'Y'}, 'two': 2} }
+ p2.merge(p3)
+ p1.merge(p2)
+ p1.interpolate()
+ self.assertEqual(p1.as_dict(), r)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/reclass/values/value.py b/reclass/values/value.py
index 74ef272..7a855ad 100644
--- a/reclass/values/value.py
+++ b/reclass/values/value.py
@@ -17,6 +17,7 @@
def __init__(self, value, settings, uri):
self._settings = settings
self._uri = uri
+ self._overwrite = False
if isinstance(value, str):
try:
self._item = self._parser.parse(value, self._settings)
@@ -30,6 +31,14 @@
else:
self._item = ScaItem(value, self._settings)
+ @property
+ def overwrite(self):
+ return self._overwrite
+
+ @overwrite.setter
+ def overwrite(self, overwrite):
+ self._overwrite = overwrite
+
def uri(self):
return self._uri
diff --git a/reclass/values/valuelist.py b/reclass/values/valuelist.py
index fc0eaad..460dff0 100644
--- a/reclass/values/valuelist.py
+++ b/reclass/values/valuelist.py
@@ -104,7 +104,7 @@
else:
raise e
- if output is None:
+ if output is None or value.overwrite:
output = new
deepCopied = False
else:
@@ -124,6 +124,7 @@
raise TypeError('Cannot merge %s over %s' % (repr(self._values[n]), repr(self._values[n-1])))
else:
output = new
+ deepCopied = False
if isinstance(output, (dict, list)) and last_error is not None:
raise last_error