Skip to content
Permalink
Browse files

Minor changes to heat & nova collectors, bug-fix in docker collector

  • Loading branch information...
svoorakk committed Dec 6, 2018
1 parent 0201a79 commit f84aec1cd8a5a4540c0b4572fc5eba46d19b41c2
@@ -101,6 +101,7 @@ def update_graph_db(self, event, body):
event_source = body.get("Type", None)
LOG.info("[SWARM] Processing event received: %s", event)
LOG.info("SWARM-----UUID----- %s", uuid)
# TODO: Needs modifications to support docker compose services
try:
if event in ADD_EVENTS:
time.sleep(2)
@@ -115,15 +116,16 @@ def update_graph_db(self, event, body):
x.attrs['Id'] == uuid), None)
self._add_container(container, now_ts)
if body['Action'] == 'start':
task_id = body['Actor']['Attributes'][
'com.docker.swarm.task.id']
service = self.swarm_manager.services.get(body['Actor']['Attributes'][
'com.docker.swarm.service.id'])
#service = next((x for x in self.swarm_manager.services.list() if
# x.attrs['ID'] == uuid), None)
task = next((x for x in service.tasks() if
x['ID'] == task_id), None)
self._add_task(task, now_ts)
if 'com.docker.swarm.task.id' in body['Actor']['Attributes']:
task_id = body['Actor']['Attributes'][
'com.docker.swarm.task.id']
service = self.swarm_manager.services.get(body['Actor']['Attributes'][
'com.docker.swarm.service.id'])
#service = next((x for x in self.swarm_manager.services.list() if
# x.attrs['ID'] == uuid), None)
task = next((x for x in service.tasks() if
x['ID'] == task_id), None)
self._add_task(task, now_ts)
elif event in DELETE_EVENTS:
LOG.info("SWARM: deleting stack:\n")
if body['Type'] == 'container':
@@ -140,7 +140,11 @@ def _get_workload_output_params(self, workload_name):
res = dict()
params = dict()

outputs = self.heat.stacks.get(workload_name).outputs
workload = self.heat.stacks.get(workload_name)
if hasattr(workload, 'outputs'):
outputs = self.heat.stacks.get(workload_name).outputs
else:
outputs = list()
for output in outputs:
output_key = str(output['output_key'])
if output_key.startswith('vm_'):
@@ -79,11 +79,12 @@ def _process_event(self, timestamp, event, body):
:param body: THe Event data.
"""
default = "UNDEFINED"
uuid = body.get("payload", dict()).get("instance_id", default)
vcpus = body.get("payload", dict()).get("vcpus", default)
mem = body.get("payload", dict()).get("memory_mb", default)
name = body.get("payload", dict()).get("display_name", default)
hostname = body.get("payload", dict()).get("host", default)
payload = body.get("payload", dict())
uuid = payload.get("instance_id", default)
vcpus = payload.get("vcpus", default)
mem = payload.get("memory_mb", default)
name = payload.get("display_name", default)
hostname = payload.get("host", default)

# Get Libvirt Instance
libvirt_instance = ""
@@ -99,6 +99,7 @@ def _cb_event(self, body, message):
try:
event = body['event_type']
LOG.info("event: %s", event)
#LOG.info("Event Data: %s", body)
if event in EVENTS:
self.events_manager.dispatch_event(event, body)
message.ack()
@@ -19,9 +19,9 @@
author='Intel Labs Europe',
packages=['landscaper'],
requires=['py2neo==3.1.2', 'networkx==1.11', 'kombu==4.1.0',
'pycurl==7.43.0', 'rfc3986==0.4.1', 'flask==0.12.1',
'pycurl==7.43.0', 'rfc3986==0.4.1', 'flask==0.12.3',
'keystoneauth1==2.18', 'pythoncinderclient==1.11.0',
'pythonheatclient==1.8.0', 'pythonkeystoneclient==3.10.0',
'pythonneutronclient==6.1.0', 'pythonnovaclient==7.1.0',
'gunicorn == 19.7.1', 'paramiko==2.4.0', 'docker-py==1.10.6',
'gunicorn == 19.7.1', 'paramiko==2.4.1', 'docker-py==1.10.6',
'flask_cors==3.0.3'])
@@ -0,0 +1,160 @@
# Copyright (c) 2017, Intel Research and Development Ireland Ltd.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""
Utilities used for testing.
"""
import collections
import ConfigParser
import random
import string
import os

EdgeChange = collections.namedtuple('EdgeChange', 'edge original changed')
NodeChange = collections.namedtuple('NodeChange', 'node original changed')

TEST_CONFIG_FILE = "/home/iolie/landscaper/tests/data/tmp_config.conf"


def compare_graph(first, second):
"""
Compares the second graph to the first graph and returns the changes in the
second graph.
:param first: A networkx (sub)graph.
:param before: A networkx (sub)graph.
:returns A dict with changes.
"""
changes = {'added': [],
'removed': [],
'added_edge': [],
'removed_edge': [],
'node_changes': [],
'edge_changes': []}
for node in second.nodes():
if node not in first.nodes():
# add missing nodes
if node not in changes['added']:
changes['added'].append(node)
for edge in second.out_edges([node]):
src = edge[1]
if src not in first.nodes() and src not in changes['added']:
changes['added'].append(src)
changes['added_edge'].append(edge)
else:
if first.node[node] != second.node[node]:
changes['node_changes'].append((node, first.node[node],
second.node[node]))
for node in first.nodes():
if node not in second.nodes():
changes['removed'].append(node)
for edge in first.out_edges([node]):
changes['removed_edge'].append(edge)
else:
# node exists lets check the edges.
for edge_data in second.out_edges([node], data=True):
edge = edge_data[0:2]
if edge not in first.out_edges([node]):
changes['added_edge'].append(edge)
else:
changed_attrs = edge_data[2]
orig_attrs = _find_matching_edge(edge, first)[2]
if orig_attrs != changed_attrs:
change = EdgeChange(edge, orig_attrs, changed_attrs)
changes['edge_changes'].append(change)

for edge in first.out_edges([node]):
if edge not in second.out_edges([node]):
changes['removed_edge'].append(edge)
return changes


def _find_matching_edge(edge, graph):
"""
Retrieve an edge matching the edge inserted from the graph.
:param edge: The edge to find.
:param graph: The graph to find it in.
:return: The edge including attributes.
"""
edges_data = graph.out_edges([edge[0]], data=True)
edges = [edge_data[0:2] for edge_data in edges_data]
matching_edge_index = edges.index(edge)
return edges_data[matching_edge_index]


def write_config(config_params, config_file):
"""
Creates a test configuration for testing.
"""
cfgfile = open(config_file, 'w+')
config = ConfigParser.ConfigParser()
for section, attributes in config_params.iteritems():
config.add_section(section)
for attribute_k, attribute_v in attributes.iteritems():
config.set(section, attribute_k, attribute_v)
config.write(cfgfile)
cfgfile.close()


def create_test_config():
""""
Creates a sample test configuration used for testing and writes this
to the testing data directory.
"""
gdb_env = "USE_TEST_GDB"
if gdb_env not in os.environ:
msg = "Set '{}' to true, to run these tests".format(gdb_env)
raise AttributeError(msg)
if os.environ[gdb_env].lower() != "true":
msg = "Functionality for setting {} to false not ready".format(gdb_env)
raise AttributeError(msg)

user_env = "NEO4J_USER"
pass_env = "NEO4J_PASS"

if user_env not in os.environ or pass_env not in os.environ:
err = "{} and {} needed for the test neo4j database.".format(user_env,
pass_env)
raise AttributeError(err)

username = os.environ[user_env]
password = os.environ[pass_env]
test_config = {"neo4j": {"url": "http://localhost:7474/db/data",
"user": username, "password": password, "use_bolt": "false"},
"general": {"graph_db": "Neo4jGDB", "flush": False,
"event_listeners": "", "collectors": ""},
"physical_layer": {"machines": "machine-A"}}

# Add RabbitMQ listener configs
test_config['rabbitmq'] = {}
conf_vars = ['rb_name', 'rb_password', 'rb_host', 'rb_port', 'topic',
'notification_queue', 'exchanges']
for conf_var in conf_vars:
test_config['rabbitmq'][conf_var] = random_string(8)

write_config(test_config, TEST_CONFIG_FILE)


def remove_test_config():
"""
Remove the test configuration from the data directory.
"""
if os.path.isfile(TEST_CONFIG_FILE):
os.remove(TEST_CONFIG_FILE)


def random_string(length):
"""
Generate a random string.
:param length: Length of the random string
"""
return ''.join(random.choice(string.ascii_letters) for _ in range(length))

0 comments on commit f84aec1

Please sign in to comment.
You can’t perform that action at this time.