1 #######################################################################################
2 # Copyright ETSI Contributors and Others.
4 # Licensed under the Apache License, Version 2.0 (the "License");
5 # you may not use this file except in compliance with the License.
6 # You may obtain a copy of the License at
8 # http://www.apache.org/licenses/LICENSE-2.0
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
14 # See the License for the specific language governing permissions and
15 # limitations under the License.
16 #######################################################################################
18 from datetime
import datetime
, timedelta
23 from airflow
.decorators
import dag
, task
24 from airflow
.operators
.python
import get_current_context
25 from osm_mon
.core
.common_db
import CommonDbClient
26 from osm_mon
.core
.config
import Config
27 from osm_mon
.core
.message_bus_client
import MessageBusClient
30 logger
= logging
.getLogger("airflow.task")
36 "depends_on_past": False,
38 "retry_delay": timedelta(seconds
=5),
40 description
="Webhook callback for VDU alarm from Prometheus AlertManager",
41 is_paused_upon_creation
=False,
42 schedule_interval
=None,
43 start_date
=datetime(2022, 1, 1),
44 tags
=["osm", "webhook"],
47 @task(task_id
="main_task")
49 logger
.debug("Running main task...")
50 context
= get_current_context()
51 conf
= context
["dag_run"].conf
52 for alarm
in conf
["alerts"]:
53 logger
.info("VDU alarm:")
54 status
= alarm
["status"]
55 logger
.info(f
" status: {status}")
56 logger
.info(f
' annotations: {alarm["annotations"]}')
57 logger
.info(f
' startsAt: {alarm["startsAt"]}')
58 logger
.info(f
' endsAt: {alarm["endsAt"]}')
59 logger
.info(f
' labels: {alarm["labels"]}')
61 if alarm
["labels"]["alertname"] != "vdu_down":
64 common_db
= CommonDbClient(config
)
65 ns_id
= alarm
["labels"]["ns_id"]
66 vdu_name
= alarm
["labels"]["vdu_name"]
67 vnf_member_index
= alarm
["labels"]["vnf_member_index"]
68 vm_id
= alarm
["labels"]["vm_id"]
69 if status
== "firing":
70 # Searching alerting rule in MongoDB
72 f
"Searching healing alert rule in MongoDB: ns_id {ns_id}, "
73 f
"vnf_member_index {vnf_member_index}, "
74 f
"vdu_name {vdu_name}, "
77 alert
= common_db
.get_alert(
79 vnf_member_index
=vnf_member_index
,
82 action_type
="healing",
85 logger
.info("Found an alert rule:")
88 common_db
.update_alert_status(
89 uuid
=alert
["uuid"], alarm_status
="alarm"
91 # Get VNFR from MongoDB
92 vnfr
= common_db
.get_vnfr(
93 nsr_id
=ns_id
, member_index
=vnf_member_index
96 f
"Found VNFR ns_id: {ns_id}, vnf_member_index: {vnf_member_index}"
99 for vdu
in vnfr
.get("vdur", []):
100 if vdu
["vim-id"] == vm_id
:
101 count_index
= vdu
["count-index"]
103 if count_index
is None:
104 logger
.error(f
"VDU {vm_id} not found in VNFR")
106 # Auto-healing type rule
107 vnf_id
= alarm
["labels"]["vnf_id"]
108 msg_bus
= MessageBusClient(config
)
109 loop
= asyncio
.get_event_loop()
110 _id
= str(uuid
.uuid4())
112 vdu_id
= alert
["action"]["vdu-id"]
113 day1
= alert
["action"]["day1"]
114 projects_read
= vnfr
["_admin"]["projects_read"]
115 projects_write
= vnfr
["_admin"]["projects_write"]
117 "lcmOperationType": "heal",
118 "nsInstanceId": ns_id
,
121 "vnfInstanceId": vnf_id
,
123 "additionalParams": {
128 "count-index": count_index
,
139 "operationState": "PROCESSING",
140 "statusEnteredTime": now
,
141 "nsInstanceId": ns_id
,
142 "member-vnf-index": vnf_member_index
,
143 "lcmOperationType": "heal",
145 "location": "default",
146 "isAutomaticInvocation": True,
147 "operationParams": params
,
148 "isCancelPending": False,
150 "self": "/osm/nslcm/v1/ns_lcm_op_occs/" + _id
,
151 "nsInstance": "/osm/nslcm/v1/ns_instances/" + ns_id
,
154 "projects_read": projects_read
,
155 "projects_write": projects_write
,
158 common_db
.create_nslcmop(nslcmop
)
159 logger
.info("Sending heal action message:")
161 loop
.run_until_complete(msg_bus
.aiowrite("ns", "heal", nslcmop
))
163 logger
.info("No alert rule was found")
164 elif status
== "resolved":
165 # Searching alerting rule in MongoDB
167 f
"Searching alert rule in MongoDB: ns_id {ns_id}, "
168 f
"vnf_member_index {vnf_member_index}, "
169 f
"vdu_name {vdu_name}, "
172 alert
= common_db
.get_alert(
174 vnf_member_index
=vnf_member_index
,
177 action_type
="healing",
180 logger
.info("Found an alert rule, updating status")
181 # Update alert status
182 common_db
.update_alert_status(uuid
=alert
["uuid"], alarm_status
="ok")