Skip to content

Commit

Permalink
dsl: improve artifact and operation translation.
Browse files Browse the repository at this point in the history
  • Loading branch information
aszs committed Oct 27, 2024
1 parent 6e508d4 commit 163d5e4
Show file tree
Hide file tree
Showing 4 changed files with 29 additions and 13 deletions.
7 changes: 4 additions & 3 deletions tests/test_dsl.py
Original file line number Diff line number Diff line change
Expand Up @@ -510,19 +510,20 @@ def test_example_template():
assert src_tpl == tosca_tpl2
tosca_tpl3 = _to_yaml(example_operation_on_template_python, False)
wordpress_db = tosca_tpl3["topology_template"]["node_templates"]["wordpress_db"]
wordpress_db["artifacts"] = {
assert wordpress_db["artifacts"] == {
"db_content": {
"type": "tosca.artifacts.File",
"file": "files/wordpress_db_content.txt",
}
}
wordpress_db["interfaces"] = {
assert wordpress_db["interfaces"] == {
"Standard": {
"type": "tosca.interfaces.node.lifecycle.Standard",
"operations": {
"create": {
"implementation": {"primary": "db_create.sh"},
"inputs": {"db_data": {"get_artifact": ["SELF", "db_content"]}},
"inputs": {"db_data": {"get_artifact": ["SELF", "db_content"]}
},
}
},
}
Expand Down
5 changes: 2 additions & 3 deletions tosca-package/tosca/_tosca.py
Original file line number Diff line number Diff line change
Expand Up @@ -2782,9 +2782,6 @@ def _get_instance_fields(self):
elif not field and name[0] != "_" and is_data_field(value):
# attribute is not part of class definition, try to deduce from the value's type
field = _Tosca_Field.infer_field(self.__class__, name, value)
if field.tosca_field_type != ToscaFieldType.property:
# the value was a data value or unrecognized, nothing to convert
continue
field.default = MISSING # this whole field was missing
yield name, (field, value)
elif isinstance(field, _Tosca_Field):
Expand Down Expand Up @@ -3427,6 +3424,8 @@ def __getattr__(self, name):
else:
# this is only called when defining an operation on a type so reset query to be relative
attr._path = [".", attr.field.as_ref_expr()]
elif isinstance(attr, ArtifactType):
return _ArtifactProxy(name)
return attr

def find_artifact(self, name_or_tpl):
Expand Down
11 changes: 7 additions & 4 deletions tosca-package/tosca/yaml2python.py
Original file line number Diff line number Diff line change
Expand Up @@ -802,6 +802,8 @@ def _prop_decl(
default_value: Any = MISSING
if "default" in prop.schema.schema:
default_value = prop.schema.schema["default"]
elif "value" in prop.schema.schema: # special case for topology outputs
default_value = prop.schema.schema["value"]
elif not prop.required:
default_value = None
typename = self._prop_type(prop.schema)
Expand Down Expand Up @@ -1271,7 +1273,7 @@ def get_configurator_decl(self, op: OperationDef) -> Tuple[str, Dict[str, Any]]:
else None
)
cmd = ""
if kw is None:
if kw is None or kw["primary"]:
if isinstance(op.implementation, dict):
artifact = op.implementation.get("primary")
kw = op.implementation.copy()
Expand All @@ -1281,11 +1283,12 @@ def get_configurator_decl(self, op: OperationDef) -> Tuple[str, Dict[str, Any]]:
kw["inputs"] = op.inputs
if isinstance(artifact, str):
artifact, toscaname = self._get_name(artifact)
if hasattr(self, artifact):
tname = toscaname or artifact
if op.node_template and tname in op.node_template.artifacts:
# add direct reference to allow static type checking
cmd = f"self.{artifact}.execute("
cmd = f"self.{artifact}.execute"
if not cmd and artifact:
cmd = f"self.find_artifact({self.value2python_repr(artifact)})"
cmd = f"self.find_artifact({self.value2python_repr(artifact)}).execute"
else:
cmd = kw["className"]
module, sep, klass = cmd.rpartition(".")
Expand Down
19 changes: 16 additions & 3 deletions unfurl/yamlloader.py
Original file line number Diff line number Diff line change
Expand Up @@ -349,14 +349,27 @@ def find_implementation(self, op: OperationDef) -> Optional[Dict[str, Any]]:
from . import (
configurators,
) # need to import configurators to get short names # noqa: F401
from .spec import NodeSpec

inputs = op.inputs if op.inputs is not None else {}
if not op._source and self.manifest:
op._source = self.manifest.get_base_dir()
node = None
if self.manifest:
if not op._source:
op._source = self.manifest.get_base_dir()
if self.manifest.tosca and self.manifest.tosca.topology:
if op.node_template:
node_template = op.node_template
else:
ntype = op.ntype.type if op.ntype else "tosca:Root"
topology = self.manifest.tosca.topology.topology_template
nname = f"_{ntype}"
node_template = topology.add_template(nname, dict(type=ntype, imported="ignore"))
del topology.node_templates[nname]
node = NodeSpec(node_template, self.manifest.tosca.topology)
return cast(
Optional[Dict[str, Any]],
_get_config_spec_args_from_implementation(
op, inputs, None, None, safe_mode=self.get_safe_mode()
op, inputs, node, None, safe_mode=self.get_safe_mode()
),
)

Expand Down

0 comments on commit 163d5e4

Please sign in to comment.