Commit 29a7b31f authored by Spiros Koulouzis's avatar Spiros Koulouzis

set min number of VMs based on the swarm default workers and masters

parent 8760f131
......@@ -7,7 +7,6 @@
<change beforePath="$PROJECT_DIR$/.idea/workspace.xml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/workspace.xml" afterDir="false" />
<change beforePath="$PROJECT_DIR$/src/planner/planner.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/planner/planner.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/src/planner/simple_spec_alayzer.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/planner/simple_spec_alayzer.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/src/planner/specification_analyzer.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/planner/specification_analyzer.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/src/rpc_server.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/rpc_server.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/src/utils/tosca.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/utils/tosca.py" afterDir="false" />
</list>
......@@ -212,7 +211,14 @@
<option name="project" value="LOCAL" />
<updated>1571415019998</updated>
</task>
<option name="localTasksCounter" value="14" />
<task id="LOCAL-00014" summary="set default properties">
<created>1571677538860</created>
<option name="number" value="00014" />
<option name="presentableId" value="LOCAL-00014" />
<option name="project" value="LOCAL" />
<updated>1571677538860</updated>
</task>
<option name="localTasksCounter" value="15" />
<servers />
</component>
<component name="Vcs.Log.Tabs.Properties">
......@@ -241,7 +247,8 @@
<MESSAGE value="added libs in setup" />
<MESSAGE value="fixed invalid type" />
<MESSAGE value="added comments" />
<option name="LAST_COMMIT_MESSAGE" value="added comments" />
<MESSAGE value="set default properties" />
<option name="LAST_COMMIT_MESSAGE" value="set default properties" />
</component>
<component name="XDebuggerManager">
<breakpoint-manager>
......@@ -253,28 +260,18 @@
</line-breakpoint>
<line-breakpoint enabled="true" suspend="THREAD" type="python-line">
<url>file://$PROJECT_DIR$/src/utils/tosca.py</url>
<line>20</line>
<line>21</line>
<option name="timeStamp" value="128" />
</line-breakpoint>
<line-breakpoint enabled="true" suspend="THREAD" type="python-line">
<url>file://$PROJECT_DIR$/src/planner/planner.py</url>
<line>173</line>
<option name="timeStamp" value="218" />
<url>file://$PROJECT_DIR$/src/rpc_server.py</url>
<line>117</line>
<option name="timeStamp" value="255" />
</line-breakpoint>
<line-breakpoint enabled="true" suspend="THREAD" type="python-line">
<url>file://$PROJECT_DIR$/src/planner/simple_spec_alayzer.py</url>
<url>file://$PROJECT_DIR$/src/utils/TOSCA_parser.py</url>
<line>67</line>
<option name="timeStamp" value="293" />
</line-breakpoint>
<line-breakpoint enabled="true" suspend="THREAD" type="python-line">
<url>file://$PROJECT_DIR$/src/planner/simple_spec_alayzer.py</url>
<line>68</line>
<option name="timeStamp" value="294" />
</line-breakpoint>
<line-breakpoint enabled="true" suspend="THREAD" type="python-line">
<url>file://$PROJECT_DIR$/src/planner/simple_spec_alayzer.py</url>
<line>88</line>
<option name="timeStamp" value="295" />
<option name="timeStamp" value="256" />
</line-breakpoint>
</breakpoints>
<default-breakpoints>
......
......@@ -38,13 +38,30 @@ class Planner:
# Get root performance, version requirements and set specs to required node
specification_analyzer = SimpleAnalyzer(self.tosca_template)
nodes_with_new_specifications = specification_analyzer.set_node_specifications()
for new_spec_node in nodes_with_new_specifications:
logging.info('new_spec_node.name : ' + new_spec_node.name)
for index, node_in_temple in enumerate(self.tosca_template.nodetemplates):
if new_spec_node.name == node_in_temple.name:
self.tosca_template.nodetemplates[index] = new_spec_node
break
specification_analyzer = SimpleAnalyzer(self.tosca_template)
nodes_with_new_relationship_occurrences = specification_analyzer.set_relationship_occurrences()
added_node_names = []
for new_spec_occurrences in nodes_with_new_relationship_occurrences:
for index, node_in_temple in enumerate(self.tosca_template.nodetemplates):
if new_spec_occurrences.name == node_in_temple.name:
added_node_names.append(new_spec_occurrences.name)
self.tosca_template.nodetemplates[index] = new_spec_occurrences
break
for new_spec_occurrences in nodes_with_new_relationship_occurrences:
if new_spec_occurrences.name not in added_node_names:
self.tosca_template.nodetemplates.append(new_spec_occurrences)
return self.tosca_template
def get_node_template_property(self, prop_key, node_prop_dict):
prop_value = self.spec_service.get_property(prop_key)
if prop_value:
......@@ -66,7 +83,7 @@ class Planner:
for node in self.tosca_template.nodetemplates:
logging.info('Resolving requirements for: ' + node.name)
self.add_required_nodes(node)
return self.required_nodes
return self.add_required_nodes_to_template(self.required_nodes)
def add_required_nodes(self, node):
"""Adds the required nodes in self.required_nodes for an input node."""
......
import copy
from toscaparser.nodetemplate import NodeTemplate
from toscaparser.properties import Property
......@@ -13,7 +15,49 @@ class SimpleAnalyzer(SpecificationAnalyzer):
super(SimpleAnalyzer, self).__init__(tosca_template)
def set_relationship_occurrences(self):
return None
return_nodes = []
# nodes_with_occurrences_in_requirements = tosca_util.get_nodes_with_occurrences_in_requirements(
# self.tosca_template.nodetemplates)
orchestrator_nodes = tosca_util.get_nodes_by_type('tosca.nodes.ARTICONF.Orchestrator',
self.tosca_template.nodetemplates, self.all_node_types,
self.all_custom_def)
min_num_of_vm = orchestrator_nodes[0].get_property_value('masters_num')
min_num_of_vm += orchestrator_nodes[0].get_property_value('workers_num')
topology_nodes = tosca_util.get_nodes_by_type('tosca.nodes.ARTICONF.VM.topology',
self.tosca_template.nodetemplates, self.all_node_types,
self.all_custom_def)
# for requirement in topology_nodes[0].requirements:
# requirement_dict = requirement[next(iter(requirement))]
# if requirement_dict['capability'] == 'tosca.capabilities.ARTICONF.VM':
# requirement_dict['occurrences'] = min_num_of_vm
vm_nodes = tosca_util.get_nodes_by_type('tosca.nodes.ARTICONF.VM.Compute',
self.tosca_template.nodetemplates, self.all_node_types,
self.all_custom_def)
for i in range(len(vm_nodes), min_num_of_vm):
old_vm_name = vm_nodes[0].name
new_vm = copy.deepcopy(vm_nodes[0])
new_vm_name = new_vm.name + '_' + str(i)
new_vm.name = new_vm_name
templates = new_vm.templates.pop(old_vm_name)
new_vm.templates[new_vm_name] = templates
return_nodes.append(new_vm)
for requirement in topology_nodes[0].requirements:
requirement_key = next(iter(requirement))
requirement_value = requirement[requirement_key]
if requirement_value['capability'] == 'tosca.capabilities.ARTICONF.VM':
new_requirement = copy.deepcopy(requirement)
new_requirement[requirement_key]['node'] = new_vm.name
topology_nodes[0].requirements.append(new_requirement)
return_nodes.append(topology_nodes[0])
break
return return_nodes
def set_node_specifications(self):
nodes_to_implement_policies = self.get_nodes_to_implement_policy()
......@@ -65,7 +109,9 @@ class SimpleAnalyzer(SpecificationAnalyzer):
affected_node.templates[next(iter(affected_node.templates))]['properties'] = default_properties
else:
for prop_name in affected_node.templates[next(iter(affected_node.templates))]['properties']:
if 'required' in affected_node.templates[next(iter(affected_node.templates))]['properties'][prop_name] and 'type' in affected_node.templates[next(iter(affected_node.templates))]['properties'][prop_name]:
if 'required' in affected_node.templates[next(iter(affected_node.templates))]['properties'][
prop_name] and 'type' in \
affected_node.templates[next(iter(affected_node.templates))]['properties'][prop_name]:
# del affected_node.templates[next(iter(affected_node.templates))]['properties'][prop_name]
affected_node.templates[next(iter(affected_node.templates))]['properties'][prop_name] = None
affected_node.templates[next(iter(affected_node.templates))]['properties'].update(default_properties)
......@@ -86,7 +132,8 @@ class SimpleAnalyzer(SpecificationAnalyzer):
return affected_node
def get_defult_value(self, node_property):
if isinstance(node_property.value, dict) and 'required' in node_property.value and 'type' in node_property.value:
if isinstance(node_property.value,
dict) and 'required' in node_property.value and 'type' in node_property.value:
if node_property.value['required']:
default_prop = {}
if 'default' in node_property.value:
......
......@@ -113,10 +113,9 @@ if __name__ == "__main__":
conf = {'url': "http://host"}
spec_service = SpecService(conf)
test_planner = Planner(tosca_file_path, spec_service)
test_planner_required_nodes = test_planner.resolve_requirements()
test_planner.add_required_nodes_to_template(test_planner_required_nodes)
test_planner_required_nodes = test_planner.set_infrastructure_specifications()
template = tosca_util.get_tosca_template_2_topology_template(test_planner.tosca_template)
tosca_template = test_planner.resolve_requirements()
tosca_template = test_planner.set_infrastructure_specifications()
template = tosca_util.get_tosca_template_2_topology_template(tosca_template)
logger.info("template ----: \n" + template)
else:
logger.info("Input args: " + sys.argv[0] + ' ' + sys.argv[1] + ' ' + sys.argv[2])
......
import copy
from itertools import chain
from toscaparser import tosca_template
from toscaparser.elements.nodetype import NodeType
from toscaparser.nodetemplate import NodeTemplate
......@@ -12,7 +13,7 @@ node_type_key_names_to_remove = ['capabilities', 'derived_from']
def get_node_type_name(node):
"""Returns the requirements for an input node as described in the template not in the node's definition """
"""Returns the node's type name as string"""
if isinstance(node, NodeTemplate):
if node.type:
if node.type and isinstance(node.type, str):
......@@ -49,6 +50,7 @@ def get_parent_type(node):
def get_node_type_requirements(type_name, all_nodes):
"""Returns the requirements for an input node as described in the template not in the node's definition """
def_type = all_nodes[type_name]
if 'requirements' in def_type.keys():
return def_type['requirements']
......@@ -119,9 +121,9 @@ def get_tosca_template_2_topology_template(template):
tp = TOSCAParser()
yaml_str = tp.tosca_template2_yaml(template)
tosca_template_dict = yaml.load(yaml_str, Loader=yaml.FullLoader)
tosca_template = tosca_template_dict['tosca_template']
this_tosca_template = tosca_template_dict['tosca_template']
tosca_template_dict.pop('tosca_template')
tosca_template_dict['topology_template'] = tosca_template
tosca_template_dict['topology_template'] = this_tosca_template
if template.policies and 'policies' not in tosca_template_dict['topology_template']:
policies_list = []
......@@ -155,18 +157,25 @@ def set_node_properties(node, properties):
return node
def get_node_by_type(node_type, all_nodes):
return all_nodes[node_type]
def get_nodes_by_type(node_type, nodes, all_node_types, all_custom_def):
nodes_by_type = []
for node in nodes:
if node.type == node_type:
nodes_by_type.append(node)
break
elif node_type in get_all_ancestors_types(node, all_node_types, all_custom_def):
nodes_by_type.append(node)
return nodes_by_type
def get_all_ancestors_types(child_node, all_nodes, all_custom_def, ancestors_types=None):
def get_all_ancestors_types(child_node, all_node_types, all_custom_def, ancestors_types=None):
if not ancestors_types:
ancestors_types = [get_node_type_name(child_node)]
parent_type = get_parent_type(child_node)
if parent_type:
ancestors_types.append(parent_type)
parent_type = node_type_2_node_template({'name': all_nodes[parent_type]}, all_custom_def)
get_all_ancestors_types(parent_type, all_nodes, all_custom_def, ancestors_types)
parent_type = node_type_2_node_template({'name': all_node_types[parent_type]}, all_custom_def)
get_all_ancestors_types(parent_type, all_node_types, all_custom_def, ancestors_types)
return ancestors_types
......@@ -191,3 +200,14 @@ def get_all_ancestors_properties(node, all_nodes, all_custom_def, ancestors_prop
ancestors_properties.append(ancestor_prop)
return ancestors_properties
def get_nodes_with_occurrences_in_requirements(topology_nodes):
nodes_with_occurrences_in_requirement = []
for node in topology_nodes:
for requirement in node.requirements:
requirement_dict = requirement[next(iter(requirement))]
if 'occurrences' in requirement_dict:
nodes_with_occurrences_in_requirement.append(node)
break
return nodes_with_occurrences_in_requirement
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment