2 # ============LICENSE_START====================================================
3 # org.onap.vvp/validation-scripts
4 # ===================================================================
5 # Copyright © 2019 AT&T Intellectual Property. All rights reserved.
6 # ===================================================================
8 # Unless otherwise specified, all software contained herein is licensed
9 # under the Apache License, Version 2.0 (the "License");
10 # you may not use this software except in compliance with the License.
11 # You may obtain a copy of the License at
13 # http://www.apache.org/licenses/LICENSE-2.0
15 # Unless required by applicable law or agreed to in writing, software
16 # distributed under the License is distributed on an "AS IS" BASIS,
17 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 # See the License for the specific language governing permissions and
19 # limitations under the License.
23 # Unless otherwise specified, all documentation contained herein is licensed
24 # under the Creative Commons License, Attribution 4.0 Intl. (the "License");
25 # you may not use this documentation except in compliance with the License.
26 # You may obtain a copy of the License at
28 # https://creativecommons.org/licenses/by/4.0/
30 # Unless required by applicable law or agreed to in writing, documentation
31 # distributed under the License is distributed on an "AS IS" BASIS,
32 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
33 # See the License for the specific language governing permissions and
34 # limitations under the License.
36 # ============LICENSE_END============================================
39 """ environment file structure
45 from tests.helpers import (
50 find_environment_file,
53 from tests.structures import Heat
54 from tests.utils.nested_files import file_is_a_nested_template
57 # Whats persistent mean? It means it goes in env.
58 # When adding an additional case, note the ","
59 # at the end of a property to make it a tuple.
60 ENV_PARAMETER_SPEC = {
61 "PLATFORM PROVIDED": [
62 {"property": ("vnf_id",), "persistent": False, "kwargs": {}},
63 {"property": ("vnf_name",), "persistent": False, "kwargs": {}},
64 {"property": ("vf_module_id",), "persistent": False, "kwargs": {}},
65 {"property": ("vf_module_index",), "persistent": False, "kwargs": {}},
66 {"property": ("vf_module_name",), "persistent": False, "kwargs": {}},
67 {"property": ("workload_context",), "persistent": False, "kwargs": {}},
68 {"property": ("environment_context",), "persistent": False, "kwargs": {}},
69 {"property": (r"^(.+?)_net_fqdn$",), "persistent": False, "kwargs": {}},
71 "ALL": [{"property": ("name",), "persistent": False, "kwargs": {}}],
73 {"property": ("image",), "persistent": True, "kwargs": {}},
74 {"property": ("flavor",), "persistent": True, "kwargs": {}},
75 {"property": ("availability_zone",), "persistent": False, "kwargs": {}},
77 "OS::Neutron::Port": [
78 {"property": ("network",), "persistent": False, "kwargs": {}},
80 "property": ("fixed_ips", "ip_address"),
82 "network_type": "external",
83 "kwargs": {"exclude_parameter": re.compile(r"^(.+?)_int_(.+?)$")},
86 "property": ("fixed_ips", "ip_address"),
88 "network_type": "internal",
89 "kwargs": {"exclude_parameter": re.compile(r"^((?!_int_).)*$")},
91 {"property": ("fixed_ips", "subnet"), "persistent": False, "kwargs": {}},
93 "property": ("fixed_ips", "allowed_address_pairs"),
95 "network_type": "external",
96 "kwargs": {"exclude_parameter": re.compile(r"^(.+?)_int_(.+?)$")},
99 "property": ("fixed_ips", "allowed_address_pairs"),
101 "network_type": "internal",
102 "kwargs": {"exclude_parameter": re.compile(r"^((?!_int_).)*$")},
105 "OS::ContrailV2::InterfaceRouteTable": [
108 "interface_route_table_routes",
109 "interface_route_table_routes_route",
115 "OS::Heat::ResourceGroup": [
117 "property": ("count",),
120 "exclude_resource": re.compile(
121 r"^(.+?)_subint_(.+?)_port_(.+?)_subinterfaces$"
126 "OS::ContrailV2::InstanceIp": [
128 "property": ("instance_ip_address",),
130 "network_type": "external",
131 "kwargs": {"exclude_resource": re.compile(r"^.*_int_.*$")},
134 "property": ("instance_ip_address",),
136 "network_type": "internal",
137 "kwargs": {"exclude_resource": re.compile(r"(?!.*_int_.*)")},
140 "property": ("subnet_uuid",),
142 "network_type": "internal",
143 "kwargs": {"exclude_resource": re.compile(r"(?!.*_int_.*)")},
146 "OS::ContrailV2::VirtualMachineInterface": [
149 "virtual_machine_interface_allowed_address_pairs",
150 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair",
151 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair_ip",
152 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair_ip_ip_prefix",
155 "network_type": "external",
156 "kwargs": {"exclude_resource": re.compile(r"(?!.*_int_.*)")},
162 def run_test_parameter(yaml_file, resource_type, *prop, **kwargs):
163 template_parameters = []
164 invalid_parameters = []
166 parameter_spec = ENV_PARAMETER_SPEC.get(
168 ) # matching spec dict on resource type
169 for spec in parameter_spec:
170 # iterating through spec dict and trying to match on property
171 if spec.get("property") == prop:
178 ): # now matching on additional kwargs passed in from test (i.e. network_type)
179 if not spec.get(k) or spec.get(k) != v:
183 if resource_type == "PLATFORM PROVIDED":
184 if file_is_a_nested_template(yaml_file):
186 "Not checking nested files for PLATFORM PROVIDED params"
188 template_parameters.append(
189 {"resource": "", "param": param_spec.get("property")[0]}
192 all_resources = False
193 if resource_type == "ALL":
195 template_parameters = get_template_parameters(
199 all_resources=all_resources,
200 ) # found the correct spec, proceeding w/ test
203 for parameter in template_parameters:
204 param = parameter.get("param")
205 persistence = param_spec.get("persistent")
207 if env_violation(yaml_file, param, spec.get("persistent")):
208 human_text = "must" if persistence else "must not"
209 human_text2 = "was not" if persistence else "was"
211 invalid_parameters.append(
212 "{} parameter {} {} be enumerated in an environment file, but "
213 "parameter {} for {} {} found.".format(
214 resource_type, prop, human_text, param, yaml_file, human_text2
218 assert not invalid_parameters, "\n".join(invalid_parameters)
221 def get_preload_excluded_parameters(yaml_file):
223 Returns set of all parameters that should not be included in the preload's
224 vnf parameters/tag-values section.
227 for resource_type, specs in ENV_PARAMETER_SPEC.items():
228 # apply to all resources if not in the format of an OpenStack resource
229 all_resources = "::" not in resource_type
231 results.extend(get_template_parameters(yaml_file, resource_type,
232 spec, all_resources))
233 return {item["param"] for item in results}
236 def get_template_parameters(yaml_file, resource_type, spec, all_resources=False):
239 heat = Heat(yaml_file)
241 resources = heat.resources
243 resources = heat.get_resource_by_type(resource_type)
245 for rid, resource_props in resources.items():
246 for param in prop_iterator(resource_props, *spec.get("property")):
247 if param and get_param(param) and param_helper(spec, get_param(param), rid):
248 # this is first getting the param
249 # then checking if its actually using get_param
250 # then checking a custom helper function (mostly for internal vs external networks)
251 parameters.append({"resource": rid, "param": get_param(param)})
256 def env_violation(yaml_file, parameter, persistent):
257 # Returns True IF there's a violation, False if everything looks good.
259 filepath, filename = os.path.split(yaml_file)
260 environment_pair = get_environment_pair(yaml_file)
261 if not environment_pair: # this is a nested file perhaps?
262 environment_pair = find_environment_file(
264 ) # we want to check parent env
265 if not environment_pair:
266 pytest.skip("unable to determine environment file for nested yaml file")
268 env_yaml = environment_pair.get("eyml")
269 parameters = env_yaml.get("parameters", {})
271 if parameters: # env file can be just parameters:
272 for param, value in parameters.items():
273 if re.match(parameter, param):
277 # confusing return. This function is looking for a violation.
278 return not persistent == in_env
281 def param_helper(spec, param, rid):
282 # helper function that has some predefined additional
283 # checkers, mainly to figure out if internal/external network
285 for k, v in spec.get("kwargs").items():
286 if k == "exclude_resource" and re.match(v, rid):
289 elif k == "exclude_parameter" and re.match(v, param):
296 @validates("R-91125")
297 def test_nova_server_image_parameter_exists_in_environment_file(yaml_file):
298 run_test_parameter(yaml_file, "OS::Nova::Server", "image")
301 @validates("R-69431")
302 def test_nova_server_flavor_parameter_exists_in_environment_file(yaml_file):
303 run_test_parameter(yaml_file, "OS::Nova::Server", "flavor")
306 @categories("environment_file")
307 @validates("R-22838", "R-99812")
308 def test_nova_server_name_parameter_doesnt_exist_in_environment_file(yaml_file):
309 run_test_parameter(yaml_file, "ALL", "name")
312 @categories("environment_file")
313 @validates("R-59568")
314 def test_nova_server_az_parameter_doesnt_exist_in_environment_file(yaml_file):
315 run_test_parameter(yaml_file, "OS::Nova::Server", "availability_zone")
318 @categories("environment_file")
319 @validates("R-20856")
320 def test_nova_server_vnf_id_parameter_doesnt_exist_in_environment_file(yaml_file):
321 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "vnf_id")
324 @categories("environment_file")
325 @validates("R-72871")
326 def test_nova_server_vf_module_id_parameter_doesnt_exist_in_environment_file(yaml_file):
327 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "vf_module_id")
330 @categories("environment_file")
331 @validates("R-37039")
332 def test_nova_server_vf_module_index_parameter_doesnt_exist_in_environment_file(
335 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "vf_module_index")
338 @categories("environment_file")
339 @validates("R-36542")
340 def test_nova_server_vnf_name_parameter_doesnt_exist_in_environment_file(yaml_file):
341 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "vnf_name")
344 @categories("environment_file")
345 @validates("R-80374")
346 def test_nova_server_vf_module_name_parameter_doesnt_exist_in_environment_file(
349 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "vf_module_name")
352 @categories("environment_file")
353 @validates("R-02691")
354 def test_nova_server_workload_context_parameter_doesnt_exist_in_environment_file(
357 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "workload_context")
360 @categories("environment_file")
361 @validates("R-13194")
362 def test_nova_server_environment_context_parameter_doesnt_exist_in_environment_file(
365 run_test_parameter(yaml_file, "PLATFORM PROVIDED", "environment_context")
368 @categories("environment_file")
369 @validates("R-29872")
370 def test_neutron_port_network_parameter_doesnt_exist_in_environment_file(yaml_file):
371 run_test_parameter(yaml_file, "OS::Neutron::Port", "network")
374 @categories("environment_file")
375 @validates("R-39841", "R-87123", "R-62590", "R-98905", "R-93030", "R-62590")
376 def test_neutron_port_external_fixedips_ipaddress_parameter_doesnt_exist_in_environment_file(
384 network_type="external",
388 @validates("R-28795", "R-97201", "R-93496", "R-90206", "R-98569", "R-93496")
389 def test_neutron_port_internal_fixedips_ipaddress_parameter_exists_in_environment_file(
397 network_type="internal",
401 @categories("environment_file")
402 @validates("R-83677", "R-80829", "R-69634", "R-22288")
403 def test_neutron_port_fixedips_subnet_parameter_doesnt_exist_in_environment_file(
407 yaml_file, "OS::Neutron::Port", "fixed_ips", "subnet", network_type="internal"
411 @categories("environment_file")
412 @validates("R-83412", "R-83418")
413 def test_neutron_port_external_aap_ip_parameter_doesnt_exist_in_environment_file(
419 "allowed_address_pairs",
421 network_type="external",
425 @categories("environment_file")
426 @validates("R-92193")
427 def test_network_fqdn_parameter_doesnt_exist_in_environment_file(yaml_file):
428 run_test_parameter(yaml_file, "PLATFORM PROVIDED", r"^(.+?)_net_fqdn$")
431 @categories("environment_file")
432 @validates("R-76682")
433 def test_contrail_route_prefixes_parameter_doesnt_exist_in_environment_file(yaml_file):
436 "OS::ContrailV2::InterfaceRouteTable",
437 "interface_route_table_routes",
438 "interface_route_table_routes_route",
442 @validates("R-50011")
443 def test_heat_rg_count_parameter_exists_in_environment_file(yaml_file):
444 run_test_parameter(yaml_file, "OS::Heat::ResourceGroup", "count")
447 @categories("environment_file")
448 @validates("R-100020", "R-100040", "R-100060", "R-100080", "R-100170")
449 def test_contrail_external_instance_ip_does_not_exist_in_environment_file(yaml_file):
452 "OS::ContrailV2::InstanceIp",
453 "instance_ip_address",
454 network_type="external",
458 @validates("R-100100", "R-100120", "R-100140", "R-100160", "R-100180")
459 def test_contrail_internal_instance_ip_does_exist_in_environment_file(yaml_file):
462 "OS::ContrailV2::InstanceIp",
463 "instance_ip_address",
464 network_type="internal",
468 @categories("environment_file")
469 @validates("R-100210", "R-100230", "R-100250", "R-100270")
470 def test_contrail_subnet_uuid_does_not_exist_in_environment_file(yaml_file):
471 run_test_parameter(yaml_file, "OS::ContrailV2::InstanceIp", "subnet_uuid")
474 @categories("environment_file")
475 @validates("R-100320", "R-100340")
476 def test_contrail_vmi_aap_does_not_exist_in_environment_file(yaml_file):
479 "OS::ContrailV2::VirtualMachineInterface",
480 "virtual_machine_interface_allowed_address_pairs",
481 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair",
482 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair_ip",
483 "virtual_machine_interface_allowed_address_pairs_allowed_address_pair_ip_ip_prefix",