Merge "Fix issue about PMJob report"

This commit is contained in:
Zuul
2024-08-29 17:25:14 +00:00
committed by Gerrit Code Review
7 changed files with 125 additions and 50 deletions

View File

@@ -507,7 +507,7 @@ class PrometheusPluginPm(PrometheusPluginPmBase, mon_base.MonitoringPlugin):
@validator.schema_nover(prometheus_plugin_schemas.AlertMessage)
def _alert(self, request, body):
result = []
result = {}
context = request.context
datetime_now = datetime.datetime.now(datetime.timezone.utc)
for alert in body['alerts']:
@@ -529,7 +529,7 @@ class PrometheusPluginPm(PrometheusPluginPmBase, mon_base.MonitoringPlugin):
pm_job, object_instance_id, sub_object_instance_id)
value = self.convert_measurement_unit(metric, value)
result.append({
entry = {
'objectType': pm_job.objectType,
'objectInstanceId': object_instance_id,
'subObjectInstanceId': sub_object_instance_id,
@@ -538,17 +538,22 @@ class PrometheusPluginPm(PrometheusPluginPmBase, mon_base.MonitoringPlugin):
'timeStamp': datetime_now,
'value': value
}]
})
}
if pm_job_id in result:
result[pm_job_id].append(entry)
else:
result[pm_job_id] = [entry]
except sol_ex.PrometheusPluginSkipped:
pass
if len(result) > 0:
if self.notification_callback:
# every job_id in body['alerts'] has same id
self.notification_callback(context, {
# Call ConductorV2
self.notification_callback(context, [{
'id': uuidutils.generate_uuid(),
'jobId': pm_job_id,
'entries': result,
})
'entries': entries
} for pm_job_id, entries in result.items()])
return result
def decompose_metrics_vnfc(self, pm_job):

View File

@@ -92,8 +92,8 @@ class PrometheusPluginConductor(object):
def store_alarm_info(self, context, alarm):
self.cast(context, 'store_alarm_info', alarm=alarm)
def store_job_info(self, context, report):
self.cast(context, 'store_job_info', report=report)
def store_job_info(self, context, reports):
self.cast(context, 'store_job_info', reports=reports)
def store_threshold_state_info(self, context, threshold_states):
self.cast(context, 'store_threshold_state_info',

View File

@@ -434,9 +434,9 @@ class ConductorV2(object):
def store_alarm_info(self, context, alarm):
self.vnffm_driver.store_alarm_info(context, alarm)
def store_job_info(self, context, report):
def store_job_info(self, context, reports):
# call pm_driver
self.vnfpm_driver.store_job_info(context, report)
self.vnfpm_driver.store_job_info(context, reports)
def store_threshold_state_info(self, context, threshold_states):
# call pm_driver

View File

@@ -33,21 +33,21 @@ class VnfPmDriverV2():
self.endpoint = CONF.v2_vnfm.endpoint
self.nfvo_client = nfvo_client.NfvoClient()
def store_job_info(self, context, report):
# store report into db
def store_job_info(self, context, reports):
for report in reports:
# store report into db
report = self._store_report(context, report)
report = self._store_report(context, report)
# update job reports
job_id = report.jobId
timestamp = report.entries[0].performanceValues[0].timeStamp
pm_job = self._update_job_reports(
context, job_id, report, timestamp, self.endpoint)
# update job reports
job_id = report.jobId
timestamp = report.entries[0].performanceValues[0].timeStamp
pm_job = self._update_job_reports(
context, job_id, report, timestamp, self.endpoint)
# Send a notify pm job request to the NFVO client.
# POST /{pmjob.callbackUri}
self.nfvo_client.send_pm_job_notification(
report, pm_job, timestamp, self.endpoint)
# Send a notify pm job request to the NFVO client.
# POST /{pmjob.callbackUri}
self.nfvo_client.send_pm_job_notification(
report, pm_job, timestamp, self.endpoint)
def store_threshold_info(self, context, threshold_states):
for threshold_state in threshold_states:

View File

@@ -288,7 +288,7 @@ def pm_event(job_id, inst_id):
def entries(body, inst_id):
return {
return [{
'id': uuidutils.generate_uuid(),
'jobId': body.get("id"),
'entries': [{
@@ -300,7 +300,7 @@ def entries(body, inst_id):
'value': 0.8
}]
}],
}
}]
def alarm(inst_id):

View File

@@ -53,12 +53,13 @@ _body_base = {
'truncatedAlerts': 0
}
_pm_job_id1 = '64e46b0e-887a-4691-8d2b-aa3d7b157e2c'
_body_pm_alert1 = {
'status': 'firing',
'labels': {
'receiver_type': 'tacker',
'function_type': 'vnfpm',
'job_id': '64e46b0e-887a-4691-8d2b-aa3d7b157e2c',
'job_id': _pm_job_id1,
'metric': 'VCpuUsageMeanVnf.'
'25b9b9d0-2461-4109-866e-a7767375415b',
'object_instance_id': '25b9b9d0-2461-4109-866e-a7767375415b'
@@ -89,6 +90,11 @@ _body_pm_alert5['labels']['metric'] = 'ByteIncomingVnfIntCp'
_body_pm_alert6 = copy.deepcopy(_body_pm_alert1)
_body_pm_alert6['labels']['metric'] = 'InvalidMetric'
# job_id and object_instance_id are changed for multiple job alerts
_body_pm_alert7 = copy.deepcopy(_body_pm_alert1)
_body_pm_alert7['labels']['job_id'] = 'pm_job_id2'
_body_pm_alert7['labels']['object_instance_id'] = 'obj_instance_id2'
_body_pm_threshold_alert1 = {
'status': 'firing',
'labels': {
@@ -138,6 +144,11 @@ _body_pm2.update({
'alerts': [_body_pm_alert5, _body_pm_alert6]
})
_body_pm3 = copy.deepcopy(_body_base)
_body_pm3.update({
'alerts': [_body_pm_alert1, _body_pm_alert1, _body_pm_alert7]
})
_body_pm_threshold1 = copy.deepcopy(_body_base)
_body_pm_threshold1.update({
'alerts': [
@@ -205,6 +216,10 @@ _pm_job2['criteria']['performanceMetric'] = ['ByteIncomingVnfIntCp']
_pm_job2['criteria']['performanceMetricGroup'] = [
'VnfInternalCp', 'VnfExternalCp']
_pm_job3 = copy.deepcopy(_pm_job)
_pm_job3['id'] = 'pm_job_id2'
_pm_job3['objectInstanceIds'] = ['obj_instance_id2']
_pm_threshold = {
'id': 'threshold_id',
'objectType': 'Vnf',
@@ -472,7 +487,7 @@ class TestPrometheusPluginPm(base.TestCase):
result = pp._alert(self.request, body=_body_pm1)
self.assertTrue(len(result) > 0)
self.assertEqual(
result[0]['objectInstanceId'],
result[_pm_job_id1][0]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
@mock.patch.object(pm_job_utils, 'get_pm_report')
@@ -489,7 +504,7 @@ class TestPrometheusPluginPm(base.TestCase):
with freezegun.freeze_time(datetime_test):
result = pp._alert(self.request, body=_body_pm2)
self.assertTrue(len(result) == 1)
self.assertEqual(result[0]["performanceMetric"],
self.assertEqual(result[_pm_job_id1][0]["performanceMetric"],
'ByteIncomingVnfIntCp')
@mock.patch.object(pm_job_utils, 'get_pm_report')
@@ -507,7 +522,7 @@ class TestPrometheusPluginPm(base.TestCase):
result = pp._alert(self.request, body=_body_pm1)
self.assertTrue(len(result) > 0)
self.assertEqual(
result[0]['objectInstanceId'],
result[_pm_job_id1][0]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
mock_pm_report.return_value = None
unload_uuidsentinel()
@@ -515,7 +530,7 @@ class TestPrometheusPluginPm(base.TestCase):
result = pp._alert(self.request, body=_body_pm1)
self.assertTrue(len(result) > 0)
self.assertEqual(
result[0]['objectInstanceId'],
result[_pm_job_id1][0]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
@mock.patch.object(pm_job_utils, 'get_pm_report')
@@ -558,9 +573,34 @@ class TestPrometheusPluginPm(base.TestCase):
result = pp._alert(self.request, body=_body_pm1)
self.assertTrue(len(result) > 0)
self.assertEqual(
result[0]['objectInstanceId'],
result[_pm_job_id1][0]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
@mock.patch.object(pm_job_utils, 'get_pm_report')
@mock.patch.object(pm_job_utils, 'get_pm_job')
def test_pm_multi_job_alerts(self, mock_pm_job, mock_pm_report):
self.config_fixture.config(
group='prometheus_plugin', performance_management=True)
return_pm_job1 = objects.PmJobV2.from_dict(_pm_job)
return_pm_job2 = objects.PmJobV2.from_dict(_pm_job3)
mock_pm_job.side_effect = [return_pm_job1, return_pm_job1,
return_pm_job2]
mock_pm_report.return_value = [objects.PerformanceReportV2.from_dict(
_pm_report)]
pp = mon_base.MonitoringPlugin.get_instance(
prometheus_plugin.PrometheusPluginPm)
unload_uuidsentinel()
with freezegun.freeze_time(datetime_test):
result = pp._alert(self.request, body=_body_pm3)
self.assertTrue(len(result) == 2)
self.assertEqual(result[_pm_job_id1][0]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
self.assertEqual(result[_pm_job_id1][1]['objectInstanceId'],
'25b9b9d0-2461-4109-866e-a7767375415b')
self.assertEqual(result['pm_job_id2'][0]['objectInstanceId'],
'obj_instance_id2')
def test_pm_error_access_info(self):
self.config_fixture.config(
group='prometheus_plugin', performance_management=True)

View File

@@ -41,36 +41,66 @@ class TestVnfPmDriverV2(base.BaseTestCase):
mock_send):
mock_create.return_value = None
mock_update.return_value = None
pm_job = objects.PmJobV2(
id='pm_job_1',
pm_job1 = objects.PmJobV2(
id='pm_job_id1',
objectTtype='VNF',
authentication=objects.SubscriptionAuthentication(
authType=["BASIC"],
authType=['BASIC'],
paramsBasic=objects.SubscriptionAuthentication_ParamsBasic(
userName='test',
password='test'
),
),
callbackUri='http://127.0.0.1/callback'
callbackUri='http://127.0.0.1/callback1'
)
report = {
"id": "fake_id",
"jobId": "fake_job_id",
"entries": [{
"objectType": "VNF",
"objectInstanceId": "instance_id_1",
"subObjectInstanceId": "subObjectInstanceId_1",
pm_job2 = objects.PmJobV2(
id='pm_job_id2',
objectTtype='VNF',
authentication=objects.SubscriptionAuthentication(
authType=['BASIC'],
paramsBasic=objects.SubscriptionAuthentication_ParamsBasic(
userName='test',
password='test'
),
),
callbackUri='http://127.0.0.1/callback2'
)
mock_update_report.side_effect = [pm_job1, pm_job2]
mock_send.return_value = None
report1 = {
'id': 'fake_id1',
'jobId': 'pm_job_id1',
'entries': [{
'objectType': 'VNF',
'objectInstanceId': 'instance_id1',
'subObjectInstanceId': 'subObjectInstanceId1',
'performanceValues': [{
'timeStamp': "2022-06-21T23:47:36.453Z",
'value': "99.0"
'timeStamp': '2022-06-21T23:47:36.453Z',
'value': '99.0'
}]
}]
}
mock_update_report.return_value = pm_job
mock_send.return_value = None
VnfPmDriverV2().store_job_info(context=self.context,
report=report)
report2 = {
'id': 'fake_id2',
'jobId': 'pm_job_id2',
'entries': [{
'objectType': 'VNF',
'objectInstanceId': 'instance_id2',
'subObjectInstanceId': 'subObjectInstanceId2',
'performanceValues': [{
'timeStamp': '2022-06-21T23:47:36.453Z',
'value': '99.0'
}]
}]
}
reports = [report1, report2]
VnfPmDriverV2().store_job_info(context=self.context, reports=reports)
call1 = mock.call(mock.ANY, 'pm_job_id1', mock.ANY, mock.ANY, mock.ANY)
call2 = mock.call(mock.ANY, 'pm_job_id2', mock.ANY, mock.ANY, mock.ANY)
mock_update_report.assert_has_calls([call1, call2])
call1 = mock.call(mock.ANY, pm_job1, mock.ANY, mock.ANY)
call2 = mock.call(mock.ANY, pm_job2, mock.ANY, mock.ANY)
mock_send.assert_has_calls([call1, call2])
@mock.patch.object(subsc_utils, 'send_notification')
@mock.patch.object(objects.base.TackerPersistentObject, 'get_by_id')