diff --git a/src/rougail/annotator/constrainte.py b/src/rougail/annotator/constrainte.py
index 5821b31c..df4d2c03 100644
--- a/src/rougail/annotator/constrainte.py
+++ b/src/rougail/annotator/constrainte.py
@@ -504,7 +504,8 @@ class ConstrainteAnnotator:
targets.append(fill.target)
#
if fill.name not in self.functions:
- raise DictConsistencyError(_('cannot find fill function {}').format(fill.name), 25)
+ xmlfiles = self.objectspace.display_xmlfiles(fill.xmlfiles)
+ raise DictConsistencyError(_(f'cannot find fill function {fill.name} in {xmlfiles}'), 25)
namespace = fill.namespace
# let's replace the target by the path
@@ -513,7 +514,8 @@ class ConstrainteAnnotator:
with_suffix=True,
)
if suffix is not None:
- raise DictConsistencyError(_(f'Cannot add fill function to "{fill.target}" only with the suffix "{suffix}"'), 26)
+ xmlfiles = self.objectspace.display_xmlfiles(fill.xmlfiles)
+ raise DictConsistencyError(_(f'Cannot add fill function to "{fill.target}" only with the suffix "{suffix}" in {xmlfiles}'), 26)
variable = self.objectspace.paths.get_variable_obj(fill.target)
value = self.objectspace.value(variable.xmlfiles)
value.type = 'calculation'
@@ -522,9 +524,15 @@ class ConstrainteAnnotator:
param_to_delete = []
for fill_idx, param in enumerate(fill.param):
if param.type not in ['suffix', 'string'] and not hasattr(param, 'text'):
- raise DictConsistencyError(_(f"All '{param.type}' variables must have a value in order to calculate {fill.target}"), 27)
- if param.type == 'suffix' and hasattr(param, 'text'):
- raise DictConsistencyError(_(f"All '{param.type}' variables must not have a value in order to calculate {fill.target}"), 28)
+ xmlfiles = self.objectspace.display_xmlfiles(fill.xmlfiles)
+ raise DictConsistencyError(_(f"All '{param.type}' variables must have a value in order to calculate {fill.target} in {xmlfiles}"), 27)
+ if param.type == 'suffix':
+ if hasattr(param, 'text'):
+ xmlfiles = self.objectspace.display_xmlfiles(fill.xmlfiles)
+ raise DictConsistencyError(_(f"All '{param.type}' variables must not have a value in order to calculate {fill.target} in {xmlfiles}"), 28)
+ if not self.objectspace.paths.variable_is_dynamic(fill.target):
+ xmlfiles = self.objectspace.display_xmlfiles(fill.xmlfiles)
+ raise DictConsistencyError(_(f'Cannot set suffix target to the none dynamic variable "{fill.target}" in {xmlfiles}'), 53)
if param.type == 'string':
if not hasattr(param, 'text'):
param.text = None
diff --git a/src/rougail/path.py b/src/rougail/path.py
index b8374b16..59899970 100644
--- a/src/rougail/path.py
+++ b/src/rougail/path.py
@@ -174,6 +174,11 @@ class Path:
return True
return name in self.variables
+ def variable_is_dynamic(self,
+ name: str,
+ ) -> bool:
+ return self._get_variable(name)['is_dynamic']
+
def _get_variable(self,
name: str,
with_suffix: bool=False,
diff --git a/tests/dictionaries/20family_dynamic_calc_suffix/00-base.xml b/tests/dictionaries/20family_dynamic_calc_suffix/00-base.xml
new file mode 100644
index 00000000..a8e758a8
--- /dev/null
+++ b/tests/dictionaries/20family_dynamic_calc_suffix/00-base.xml
@@ -0,0 +1,25 @@
+
+
+
+
+
+
+ val1
+ val2
+
+
+
+
+ val
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/tests/dictionaries/20family_dynamic_calc_suffix/__init__.py b/tests/dictionaries/20family_dynamic_calc_suffix/__init__.py
new file mode 100644
index 00000000..e69de29b
diff --git a/tests/dictionaries/20family_dynamic_calc_suffix/makedict/base.json b/tests/dictionaries/20family_dynamic_calc_suffix/makedict/base.json
new file mode 100644
index 00000000..09b64ff8
--- /dev/null
+++ b/tests/dictionaries/20family_dynamic_calc_suffix/makedict/base.json
@@ -0,0 +1 @@
+{"rougail.general.varname": ["val1", "val2"], "rougail.dynval1.vardynval1": "val1", "rougail.dynval2.vardynval2": "val2", "rougail.new.newvar": null}
diff --git a/tests/dictionaries/20family_dynamic_calc_suffix/tiramisu/__init__.py b/tests/dictionaries/20family_dynamic_calc_suffix/tiramisu/__init__.py
new file mode 100644
index 00000000..e69de29b
diff --git a/tests/dictionaries/20family_dynamic_calc_suffix/tiramisu/base.py b/tests/dictionaries/20family_dynamic_calc_suffix/tiramisu/base.py
new file mode 100644
index 00000000..f4cb9beb
--- /dev/null
+++ b/tests/dictionaries/20family_dynamic_calc_suffix/tiramisu/base.py
@@ -0,0 +1,18 @@
+from importlib.machinery import SourceFileLoader
+func = SourceFileLoader('func', 'tests/dictionaries/../eosfunc/test.py').load_module()
+for key, value in dict(locals()).items():
+ if key != ['SourceFileLoader', 'func']:
+ setattr(func, key, value)
+try:
+ from tiramisu3 import *
+except:
+ from tiramisu import *
+from rougail.tiramisu import ConvertDynOptionDescription
+option_3 = StrOption(properties=frozenset({'mandatory', 'normal'}), name='varname', doc='No change', multi=True, default=['val1', 'val2'], default_multi='val2')
+option_2 = OptionDescription(name='general', doc='general', properties=frozenset({'normal'}), children=[option_3])
+option_5 = StrOption(properties=frozenset({'normal'}), name='vardyn', doc='No change', multi=False, default=Calculation(func.calc_val, Params((ParamSuffix()), kwargs={})))
+option_4 = ConvertDynOptionDescription(name='dyn', doc='dyn', suffixes=Calculation(func.calc_value, Params((ParamOption(option_3)))), properties=frozenset({'normal'}), children=[option_5])
+option_7 = StrOption(properties=frozenset({'normal'}), name='newvar', doc='No change', multi=False)
+option_6 = OptionDescription(name='new', doc='new', properties=frozenset({'normal'}), children=[option_7])
+option_1 = OptionDescription(name='rougail', doc='rougail', children=[option_2, option_4, option_6])
+option_0 = OptionDescription(name='baseoption', doc='baseoption', children=[option_1])
diff --git a/tests/dictionaries/80family_not_dynamic_calc_suffix/00-base.xml b/tests/dictionaries/80family_not_dynamic_calc_suffix/00-base.xml
new file mode 100644
index 00000000..04b287be
--- /dev/null
+++ b/tests/dictionaries/80family_not_dynamic_calc_suffix/00-base.xml
@@ -0,0 +1,25 @@
+
+
+
+
+
+
+ val1
+ val2
+
+
+
+
+ val
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/tests/dictionaries/80family_not_dynamic_calc_suffix/__init__.py b/tests/dictionaries/80family_not_dynamic_calc_suffix/__init__.py
new file mode 100644
index 00000000..e69de29b
diff --git a/tests/dictionaries/80family_not_dynamic_calc_suffix/errno_53 b/tests/dictionaries/80family_not_dynamic_calc_suffix/errno_53
new file mode 100644
index 00000000..e69de29b