object in target
This commit is contained in:
parent
3e2d221cc4
commit
06e7196280
5 changed files with 69 additions and 98 deletions
|
@ -6,7 +6,6 @@ from typing import List, Any
|
||||||
from .variable import CONVERT_OPTION
|
from .variable import CONVERT_OPTION
|
||||||
|
|
||||||
from ..i18n import _
|
from ..i18n import _
|
||||||
from ..utils import normalize_family
|
|
||||||
from ..error import DictConsistencyError
|
from ..error import DictConsistencyError
|
||||||
from ..config import Config
|
from ..config import Config
|
||||||
|
|
||||||
|
@ -61,7 +60,7 @@ class ConstrainteAnnotator:
|
||||||
if hasattr(self.objectspace.space.constraints, 'condition'):
|
if hasattr(self.objectspace.space.constraints, 'condition'):
|
||||||
self.convert_condition_target()
|
self.convert_condition_target()
|
||||||
self.convert_xxxlist_to_variable()
|
self.convert_xxxlist_to_variable()
|
||||||
self.check_condition_fallback_optional()
|
self.check_condition_fallback()
|
||||||
self.convert_condition_source()
|
self.convert_condition_source()
|
||||||
self.check_choice_option_condition()
|
self.check_choice_option_condition()
|
||||||
self.remove_condition_with_empty_target()
|
self.remove_condition_with_empty_target()
|
||||||
|
@ -271,18 +270,17 @@ class ConstrainteAnnotator:
|
||||||
target,
|
target,
|
||||||
):
|
):
|
||||||
if target.type == 'variable':
|
if target.type == 'variable':
|
||||||
variable = self.objectspace.paths.get_variable_obj(target.name)
|
if not self.objectspace.paths.is_leader(target.name.path):
|
||||||
|
return target.name, [target.name]
|
||||||
# it's a leader, so apply property to leadership
|
# it's a leader, so apply property to leadership
|
||||||
if self.objectspace.paths.is_leader(target.name):
|
family_name = self.objectspace.paths.get_variable_family_path(target.name.path)
|
||||||
family_name = self.objectspace.paths.get_variable_family_path(target.name)
|
family = self.objectspace.paths.get_family(family_name,
|
||||||
family = self.objectspace.paths.get_family(target.name.rsplit('.', 1)[0],
|
target.name.namespace,
|
||||||
variable.namespace,
|
|
||||||
)
|
)
|
||||||
return family, family.variable
|
return family, family.variable
|
||||||
return variable, [variable]
|
|
||||||
# it's a family
|
# it's a family
|
||||||
variable = self.objectspace.paths.get_family(target.name,
|
variable = self.objectspace.paths.get_family(target.name.path,
|
||||||
None,
|
target.namespace,
|
||||||
)
|
)
|
||||||
return variable, list(variable.variable.values())
|
return variable, list(variable.variable.values())
|
||||||
|
|
||||||
|
@ -295,40 +293,36 @@ class ConstrainteAnnotator:
|
||||||
msg = _(f'target is mandatory in a condition for source "{condition.source}" '
|
msg = _(f'target is mandatory in a condition for source "{condition.source}" '
|
||||||
f'in {xmlfiles}')
|
f'in {xmlfiles}')
|
||||||
raise DictConsistencyError(msg, 9)
|
raise DictConsistencyError(msg, 9)
|
||||||
for target in condition.target:
|
remove_targets = []
|
||||||
|
for index, target in enumerate(condition.target):
|
||||||
|
try:
|
||||||
if target.type == 'variable':
|
if target.type == 'variable':
|
||||||
if condition.source == target.name:
|
if condition.source == target.name:
|
||||||
msg = f'target name and source name must be different: {condition.source}'
|
msg = f'target name and source name must be different: {condition.source}'
|
||||||
raise DictConsistencyError(_(msg), 11)
|
raise DictConsistencyError(_(msg), 11)
|
||||||
target_names = '.'.join([normalize_family(name) \
|
target.name = self.objectspace.paths.get_variable_obj(target.name)
|
||||||
for name in target.name.split('.')])
|
elif target.type == 'family':
|
||||||
try:
|
target.name = self.objectspace.paths.get_family(target.name,
|
||||||
target.name, suffix = self.objectspace.paths.get_variable_path(target_names,
|
|
||||||
condition.namespace,
|
condition.namespace,
|
||||||
)
|
)
|
||||||
if suffix:
|
|
||||||
xmlfiles = self.objectspace.display_xmlfiles(condition.xmlfiles)
|
|
||||||
msg = _(f'the target "{target.name}" in condition cannot be a dynamic '
|
|
||||||
f'variable in {xmlfiles}')
|
|
||||||
raise DictConsistencyError(msg, 21)
|
|
||||||
except DictConsistencyError as err:
|
|
||||||
# for optional variable
|
|
||||||
if not target.optional or err.errno != 42:
|
|
||||||
raise err
|
|
||||||
elif target.type == 'family':
|
|
||||||
target_path = '.'.join([normalize_family(name) \
|
|
||||||
for name in target.name.split('.')])
|
|
||||||
if not self.objectspace.paths.family_is_defined(target_path,
|
|
||||||
condition.namespace,
|
|
||||||
):
|
|
||||||
raise DictConsistencyError(_(f'cannot found family {target.name}'), 12)
|
|
||||||
target.name = target_path
|
|
||||||
elif target.type.endswith('list') and \
|
elif target.type.endswith('list') and \
|
||||||
condition.name not in ['disabled_if_in', 'disabled_if_not_in']:
|
condition.name not in ['disabled_if_in', 'disabled_if_not_in']:
|
||||||
xmlfiles = self.objectspace.display_xmlfiles(target.xmlfiles)
|
xmlfiles = self.objectspace.display_xmlfiles(target.xmlfiles)
|
||||||
msg = _(f'target "{target.type}" not allow in condition "{condition.name}" '
|
msg = _(f'target "{target.type}" not allow in condition "{condition.name}" '
|
||||||
f'in {xmlfiles}')
|
f'in {xmlfiles}')
|
||||||
raise DictConsistencyError(msg, 10)
|
raise DictConsistencyError(msg, 10)
|
||||||
|
except DictConsistencyError as err:
|
||||||
|
if err.errno != 42:
|
||||||
|
raise err
|
||||||
|
# for optional variable
|
||||||
|
if not target.optional:
|
||||||
|
xmlfiles = self.objectspace.display_xmlfiles(condition.xmlfiles)
|
||||||
|
raise DictConsistencyError(_(f'cannot found target "{target.name}" in the condition in {xmlfiles}'), 12)
|
||||||
|
remove_targets.append(index)
|
||||||
|
remove_targets.sort(reverse=True)
|
||||||
|
for index in remove_targets:
|
||||||
|
condition.target.pop(index)
|
||||||
|
|
||||||
|
|
||||||
def convert_xxxlist_to_variable(self):
|
def convert_xxxlist_to_variable(self):
|
||||||
"""transform *list to variable or family
|
"""transform *list to variable or family
|
||||||
|
@ -343,9 +337,8 @@ class ConstrainteAnnotator:
|
||||||
{}).get(target.name)
|
{}).get(target.name)
|
||||||
if listvars:
|
if listvars:
|
||||||
for listvar in listvars:
|
for listvar in listvars:
|
||||||
variable = self.objectspace.paths.get_variable_obj(listvar)
|
|
||||||
type_ = 'variable'
|
type_ = 'variable'
|
||||||
new_target = self.objectspace.target(variable.xmlfiles)
|
new_target = self.objectspace.target(listvar.xmlfiles)
|
||||||
new_target.type = type_
|
new_target.type = type_
|
||||||
new_target.name = listvar
|
new_target.name = listvar
|
||||||
new_targets.append(new_target)
|
new_targets.append(new_target)
|
||||||
|
@ -355,7 +348,7 @@ class ConstrainteAnnotator:
|
||||||
condition.target.pop(target_idx)
|
condition.target.pop(target_idx)
|
||||||
condition.target.extend(new_targets)
|
condition.target.extend(new_targets)
|
||||||
|
|
||||||
def check_condition_fallback_optional(self):
|
def check_condition_fallback(self):
|
||||||
"""a condition with a fallback **and** the source variable doesn't exist
|
"""a condition with a fallback **and** the source variable doesn't exist
|
||||||
"""
|
"""
|
||||||
remove_conditions = []
|
remove_conditions = []
|
||||||
|
@ -371,18 +364,6 @@ class ConstrainteAnnotator:
|
||||||
remove_conditions.append(idx)
|
remove_conditions.append(idx)
|
||||||
if apply_action:
|
if apply_action:
|
||||||
self.force_actions_to_variable(condition)
|
self.force_actions_to_variable(condition)
|
||||||
continue
|
|
||||||
|
|
||||||
remove_targets = []
|
|
||||||
# optional
|
|
||||||
for index, target in enumerate(condition.target):
|
|
||||||
if target.optional is True and \
|
|
||||||
not self.objectspace.paths.path_is_defined(target.name):
|
|
||||||
remove_targets.append(index)
|
|
||||||
remove_targets = list(set(remove_targets))
|
|
||||||
remove_targets.sort(reverse=True)
|
|
||||||
for index in remove_targets:
|
|
||||||
condition.target.pop(index)
|
|
||||||
remove_conditions = list(set(remove_conditions))
|
remove_conditions = list(set(remove_conditions))
|
||||||
remove_conditions.sort(reverse=True)
|
remove_conditions.sort(reverse=True)
|
||||||
for idx in remove_conditions:
|
for idx in remove_conditions:
|
||||||
|
|
|
@ -84,6 +84,7 @@ class ServiceAnnotator:
|
||||||
and build elements and its attributes (the `Options` in tiramisu terms)
|
and build elements and its attributes (the `Options` in tiramisu terms)
|
||||||
"""
|
"""
|
||||||
families = []
|
families = []
|
||||||
|
listname = '{}list'.format(elttype)
|
||||||
for elt in elts:
|
for elt in elts:
|
||||||
# try to launch _update_xxxx() function
|
# try to launch _update_xxxx() function
|
||||||
update_elt = '_update_' + elttype
|
update_elt = '_update_' + elttype
|
||||||
|
@ -99,17 +100,21 @@ class ServiceAnnotator:
|
||||||
elt.xmlfiles,
|
elt.xmlfiles,
|
||||||
)
|
)
|
||||||
family.variable = []
|
family.variable = []
|
||||||
activate_path = '.'.join([subpath, 'activate'])
|
activate_obj = self._generate_element('boolean',
|
||||||
|
'activate',
|
||||||
|
True,
|
||||||
|
elt.xmlfiles,
|
||||||
|
'.'.join([subpath, 'activate']),
|
||||||
|
)
|
||||||
for key in dir(elt):
|
for key in dir(elt):
|
||||||
if key.startswith('_') or key.endswith('_type') or key in ERASED_ATTRIBUTES:
|
if key.startswith('_') or key.endswith('_type') or key in ERASED_ATTRIBUTES:
|
||||||
continue
|
continue
|
||||||
value = getattr(elt, key)
|
value = getattr(elt, key)
|
||||||
listname = '{}list'.format(elttype)
|
|
||||||
if key == listname:
|
if key == listname:
|
||||||
self.objectspace.list_conditions.setdefault(listname,
|
self.objectspace.list_conditions.setdefault(listname,
|
||||||
{}).setdefault(
|
{}).setdefault(
|
||||||
value,
|
value,
|
||||||
[]).append(activate_path)
|
[]).append(activate_obj)
|
||||||
continue
|
continue
|
||||||
family.variable.append(self._generate_element(self._get_type(key,
|
family.variable.append(self._generate_element(self._get_type(key,
|
||||||
elttype,
|
elttype,
|
||||||
|
@ -122,12 +127,7 @@ class ServiceAnnotator:
|
||||||
))
|
))
|
||||||
# FIXME ne devrait pas etre True par défaut
|
# FIXME ne devrait pas etre True par défaut
|
||||||
# devrait etre un calcule
|
# devrait etre un calcule
|
||||||
family.variable.append(self._generate_element('boolean',
|
family.variable.append(activate_obj)
|
||||||
'activate',
|
|
||||||
True,
|
|
||||||
elt.xmlfiles,
|
|
||||||
activate_path,
|
|
||||||
))
|
|
||||||
families.append(family)
|
families.append(family)
|
||||||
return families
|
return families
|
||||||
|
|
||||||
|
@ -146,7 +146,10 @@ class ServiceAnnotator:
|
||||||
if idx:
|
if idx:
|
||||||
c_name += f'_{idx}'
|
c_name += f'_{idx}'
|
||||||
subpath = '{}.{}'.format(path, c_name)
|
subpath = '{}.{}'.format(path, c_name)
|
||||||
if not self.objectspace.paths.family_is_defined(subpath, 'services'):
|
try:
|
||||||
|
self.objectspace.paths.get_family(subpath, 'services')
|
||||||
|
except DictConsistencyError as err:
|
||||||
|
if err.errno == 42:
|
||||||
return c_name, subpath
|
return c_name, subpath
|
||||||
idx += 1
|
idx += 1
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from .i18n import _
|
from .i18n import _
|
||||||
from .error import DictConsistencyError
|
from .error import DictConsistencyError
|
||||||
from .config import Config
|
from .config import Config
|
||||||
|
from .utils import normalize_family
|
||||||
|
|
||||||
|
|
||||||
class Path:
|
class Path:
|
||||||
|
@ -48,33 +49,19 @@ class Path:
|
||||||
)
|
)
|
||||||
variableobj.path = path
|
variableobj.path = path
|
||||||
|
|
||||||
def _get_family(self,
|
|
||||||
name: str,
|
|
||||||
namespace: str=None,
|
|
||||||
):
|
|
||||||
# if main namespace, get full_path
|
|
||||||
if '.' not in name and namespace in [None, Config['variable_namespace']] and name in self.full_paths_families:
|
|
||||||
name = self.full_paths_families[name]
|
|
||||||
dico = self.families[name]
|
|
||||||
if namespace and dico['namespace'] != Config['variable_namespace'] and namespace != dico['namespace']:
|
|
||||||
raise DictConsistencyError(_(f'A family located in the "{dico["namespace"]}" namespace shall not be used in the "{namespace}" namespace'), 38)
|
|
||||||
return dico
|
|
||||||
|
|
||||||
def get_family(self,
|
def get_family(self,
|
||||||
name: str,
|
name: str,
|
||||||
namespace: str,
|
current_namespace: str,
|
||||||
) -> 'Family': # pylint: disable=C0111
|
) -> 'Family': # pylint: disable=C0111
|
||||||
return self._get_family(name, namespace)['variableobj']
|
name = '.'.join([normalize_family(subname) for subname in name.split('.')])
|
||||||
|
if name not in self.families and name in self.full_paths_families:
|
||||||
def family_is_defined(self,
|
name = self.full_paths_families[name]
|
||||||
name: str,
|
if name not in self.families:
|
||||||
namespace: str,
|
raise DictConsistencyError(_('unknown option {}').format(name), 42)
|
||||||
) -> str: # pylint: disable=C0111
|
dico = self.families[name]
|
||||||
try:
|
if current_namespace not in [Config['variable_namespace'], 'services'] and current_namespace != dico['namespace']:
|
||||||
self._get_family(name, namespace)
|
raise DictConsistencyError(_(f'A family located in the "{dico["namespace"]}" namespace shall not be used in the "{current_namespace}" namespace'), 38)
|
||||||
return True
|
return dico['variableobj']
|
||||||
except KeyError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
# Leadership
|
# Leadership
|
||||||
def set_leader(self,
|
def set_leader(self,
|
||||||
|
@ -142,13 +129,12 @@ class Path:
|
||||||
def get_variable_path(self,
|
def get_variable_path(self,
|
||||||
name: str,
|
name: str,
|
||||||
current_namespace: str,
|
current_namespace: str,
|
||||||
allow_variable_namespace: str=False,
|
|
||||||
) -> str: # pylint: disable=C0111
|
) -> str: # pylint: disable=C0111
|
||||||
dico, suffix = self._get_variable(name,
|
dico, suffix = self._get_variable(name,
|
||||||
with_suffix=True,
|
with_suffix=True,
|
||||||
)
|
)
|
||||||
namespace = dico['variableobj'].namespace
|
namespace = dico['variableobj'].namespace
|
||||||
if not allow_variable_namespace and namespace not in [Config['variable_namespace'], 'services'] and current_namespace != namespace:
|
if namespace not in [Config['variable_namespace'], 'services'] and current_namespace != namespace:
|
||||||
raise DictConsistencyError(_(f'A variable located in the "{namespace}" namespace shall not be used in the "{current_namespace}" namespace'), 41)
|
raise DictConsistencyError(_(f'A variable located in the "{namespace}" namespace shall not be used in the "{current_namespace}" namespace'), 41)
|
||||||
return dico['variableobj'].path, suffix
|
return dico['variableobj'].path, suffix
|
||||||
|
|
||||||
|
@ -168,6 +154,7 @@ class Path:
|
||||||
name: str,
|
name: str,
|
||||||
with_suffix: bool=False,
|
with_suffix: bool=False,
|
||||||
) -> str:
|
) -> str:
|
||||||
|
name = '.'.join([normalize_family(subname) for subname in name.split('.')])
|
||||||
if name not in self.variables:
|
if name not in self.variables:
|
||||||
if '.' not in name and name in self.full_paths_variables:
|
if '.' not in name and name in self.full_paths_variables:
|
||||||
name = self.full_paths_variables[name]
|
name = self.full_paths_variables[name]
|
||||||
|
|
Loading…
Reference in a new issue