2 # Licensed under the Apache License, Version 2.0 (the "License"); you may
3 # not use this file except in compliance with the License. You may obtain
4 # a copy of the License at
6 # http://www.apache.org/licenses/LICENSE-2.0
8 # Unless required by applicable law or agreed to in writing, software
9 # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
10 # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
11 # License for the specific language governing permissions and limitations
14 # Copyright 2016 RIFT.io Inc
20 from rift
.mano
.tosca_translator
.common
.utils
import _
22 from rift
.mano
.tosca_translator
.common
.utils
import dict_convert_values_to_str
26 gi
.require_version('RwYang', '1.0')
27 gi
.require_version('RwNsdYang', '1.0')
28 gi
.require_version('NsdYang', '1.0')
30 from gi
.repository
import NsdYang
31 from gi
.repository
import RwNsdYang
32 from gi
.repository
import RwYang
35 except ValueError as e
:
39 class ManoTemplate(object):
40 '''Container for full RIFT.io MANO template.'''
42 YANG_NS
= (NSD
, VNFD
) = ('nsd', 'vnfd')
43 OUTPUT_FIELDS
= (NAME
, ID
, YANG
, FILES
) = ('name', 'id', 'yang', 'files')
45 def __init__(self
, log
):
50 self
.description
= "Translated from TOSCA"
55 def output_to_yang(self
, use_gi
=False, indent
=4):
56 self
.log
.debug(_('Converting translated output to yang model.'))
59 nsd_id
= str(uuid
.uuid1())
64 nsd_cat
= RwNsdYang
.YangData_Nsd_NsdCatalog()
65 nsd
= nsd_cat
.nsd
.add()
67 nsd
.name
= self
.metadata
['name']
68 nsd
.description
= self
.description
69 nsd
.vendor
= self
.metadata
['vendor']
70 nsd
.short_name
= self
.metadata
['name']
71 nsd
.version
= self
.metadata
['version']
72 except Exception as e
:
73 self
.log
.warning(_("Unable to use YANG GI to generate "
74 "descriptors, falling back to alternate "
75 "method: {}").format(e
))
82 'name': self
.metadata
['name'],
83 'description': self
.description
,
84 'vendor': self
.metadata
['vendor'],
85 'short-name': self
.metadata
['name'],
86 'version': self
.metadata
['version'],
89 for resource
in self
.resources
:
91 if resource
.type == 'vld':
92 resource
.generate_yang_model(nsd
, vnfds
, use_gi
=use_gi
)
94 for resource
in self
.resources
:
96 if resource
.type == 'vnfd':
97 resource
.generate_yang_model(nsd
, vnfds
, use_gi
=use_gi
)
99 for resource
in self
.resources
:
101 if resource
.type != 'vnfd' and resource
.type != 'vld':
102 resource
.generate_yang_model(nsd
, vnfds
, use_gi
=use_gi
)
104 for group
in self
.groups
:
105 group
.generate_yang_model(nsd
, vnfds
, use_gi
=use_gi
)
107 for policy
in self
.policies
:
108 policy
.generate_yang_model(nsd
, vnfds
, use_gi
=use_gi
)
110 # Add input params to nsd
112 for param
in self
.parameters
:
113 nsd
.input_parameter_xpath
.append(
114 NsdYang
.YangData_Nsd_NsdCatalog_Nsd_InputParameterXpath(
115 xpath
=param
.get_xpath(),
119 nsd
['input-parameter-xpath'] = []
120 for param
in self
.parameters
:
121 nsd
['input-parameter-xpath'].append(
122 {'xpath': param
.get_xpath()})
124 # Get list of supporting files referred in template
125 # Returned format is {desc_id: [{type: type, name: filename}]}
126 # TODO (pjoseph): Currently only images and scripts are retrieved.
127 # Need to add support to get script names, charms, etc.
129 for resource
in self
.resources
:
130 resource
.get_supporting_files(other_files
)
132 for policy
in self
.policies
:
133 policy
.get_supporting_files(other_files
, desc_id
=nsd_id
)
135 self
.log
.debug(_("List of other files: {}".format(other_files
)))
137 # Do the final processing and convert each descriptor to yaml string
142 nsd_pf
= self
.get_yaml(['nsd', 'rw-nsd'], nsd_cat
)
143 nsd_id
= nsd_cat
.nsd
[0].id
144 nsd_name
= nsd_cat
.nsd
[0].name
147 nsd_name
= nsd
['name']
149 # In case of non gi proecssing,
150 # - convert all values to string
151 # - enclose in a catalog dict
152 # - prefix all keys with nsd or vnfd
153 # - Convert to YAML string
156 self
.add_cat(dict_convert_values_to_str(nsd
),
159 default_flow_style
=False)
167 if nsd_id
in other_files
:
168 nsd_out
[self
.FILES
] = other_files
[nsd_id
]
170 tpl
[self
.NSD
] = [nsd_out
]
177 vnfd_pf
= self
.get_yaml(['vnfd', 'rw-vnfd'], vnfd
)
178 vnfd_id
= vnfd
.vnfd
[0].id
179 vnfd_name
= vnfd
.vnfd
[0].name
183 vnfd_name
= vnfd
['name']
185 # In case of non gi proecssing,
186 # - convert all values to string
187 # - enclose in a catalog dict
188 # - prefix all keys with nsd or vnfd
189 # - Convert to YAML string
192 self
.add_cat(dict_convert_values_to_str(vnfd
),
195 default_flow_style
=False)
198 self
.NAME
: vnfd_name
,
203 if vnfd_id
in other_files
:
204 vnfd_out
[self
.FILES
] = other_files
[vnfd_id
]
206 tpl
[self
.VNFD
].append(vnfd_out
)
208 self
.log
.debug(_("NSD: {0}").format(tpl
[self
.NSD
]))
209 self
.log
.debug(_("VNFDs:"))
210 for vnfd
in tpl
[self
.VNFD
]:
211 self
.log
.debug(_("{0}").format(vnfd
))
215 def _get_field(self
, d
, pf
, field
='name'):
216 '''Get the name given for the descriptor'''
217 # Search within the desc for a key pf:name
219 if isinstance(d
, dict):
220 # If it is a dict, search for pf:name
224 for k
, v
in d
.items():
225 result
= self
._get
_field
(v
, pf
, field
)
228 elif isinstance(d
, list):
230 result
= self
._get
_field
(memb
, pf
, field
)
234 def prefix_dict(self
, d
, pf
):
235 '''Prefix all keys of a dict with a specific prefix:'''
236 if isinstance(d
, dict):
239 # Only prefix keys without any prefix
240 # so later we can do custom prefixing
241 # which will not get overwritten here
243 dic
[pf
+':'+key
] = self
.prefix_dict(d
[key
], pf
)
245 dic
[key
] = self
.prefix_dict(d
[key
], pf
)
247 elif isinstance(d
, list):
250 arr
.append(self
.prefix_dict(memb
, pf
))
255 def add_cat(self
, desc
, pf
):
256 return {pf
+'-catalog': {pf
: [desc
]}}
258 def get_yaml(self
, module_list
, desc
):
259 model
= RwYang
.Model
.create_libncx()
260 for module
in module_list
:
261 model
.load_module(module
)
262 return desc
.to_yaml(model
)