From c75e56f9109fa35c22ab9f7f32909a56d9069142 Mon Sep 17 00:00:00 2001 From: Konstantinos Kagkelidis Date: Mon, 30 Mar 2026 01:27:30 +0300 Subject: [PATCH] ARGO-5485 Add default profiles and reports to new tenant --- automation/argo_config.py | 4 + automation/argo_web_api.py | 149 +++++++++++++++++++++++++++++- automation/default.agg.json | 31 +++++++ automation/default.metric.json | 27 ++++++ automation/default.report.json | 33 +++++++ automation/default.services.json | 26 ++++++ automation/init_compute_engine.py | 46 ++++++++- 7 files changed, 312 insertions(+), 4 deletions(-) create mode 100644 automation/default.agg.json create mode 100644 automation/default.metric.json create mode 100644 automation/default.report.json create mode 100644 automation/default.services.json diff --git a/automation/argo_config.py b/automation/argo_config.py index 49f6a552..70499666 100644 --- a/automation/argo_config.py +++ b/automation/argo_config.py @@ -37,6 +37,10 @@ def __init__(self, path: str): self.web_api_endpoint = automation.get("web_api_endpoint") self.web_api_token = automation.get("web_api_token") self.default_ops_profile_file = automation.get("default_ops_profile_file") + self.default_metric_profile_file = automation.get("default_metric_profile_file") + self.default_agg_profile_file = automation.get("default_agg_profile_file") + self.default_services_file = automation.get("default_services_file") + self.default_report_file = automation.get("default_report_file") self.hdfs_path = run.get("hdfs_path") self.hdfs_check_path = run.get("hdfs_check_path") self.flink_path = run.get("flink_path") diff --git a/automation/argo_web_api.py b/automation/argo_web_api.py index 07c2d720..4b9fe981 100644 --- a/automation/argo_web_api.py +++ b/automation/argo_web_api.py @@ -179,6 +179,11 @@ def create_ops_profile( url, json=payload, headers=headers, timeout=REQUEST_TIMEOUT ) response.raise_for_status() + logger.info( + f"tenant: {tenant_name} ({tenant_id}) - web-api ops profile created" + ) + return response.json()["data"]["id"] + except requests.exceptions.HTTPError as e: if e.response.status_code == 409: logger.warning( @@ -188,10 +193,150 @@ def create_ops_profile( else: raise - logger.info( - f"tenant: {tenant_name} ({tenant_id}) - web-api ops profile created" + def create_metric_profile( + self, + tenant_id: str, + tenant_name: str, + tenant_access_token: str, + payload: object, + ): + """Http call to web-api to create metric profile""" + logger.debug( + f"tenant: {tenant_name} ({tenant_id}) - web-api creating default metric profile..." + ) + + url = f"https://{self.config.web_api_endpoint}/api/v2/metric_profiles" + headers = { + "x-api-key": tenant_access_token, + "Accept": "application/json", + } + try: + response = requests.post( + url, json=payload, headers=headers, timeout=REQUEST_TIMEOUT + ) + response.raise_for_status() + logger.info( + f"tenant: {tenant_name} ({tenant_id}) - web-api metric profile created" + ) + return response.json()["data"]["id"] + + except requests.exceptions.HTTPError as e: + if e.response.status_code == 409: + logger.warning( + f"tenant: {tenant_name} ({tenant_id}) - web-api metric profile already exists" + ) + return + else: + raise + + def create_aggregation_profile( + self, + tenant_id: str, + tenant_name: str, + tenant_access_token: str, + payload: object, + ): + """Http call to web-api to create aggregation profile""" + logger.debug( + f"tenant: {tenant_name} ({tenant_id}) - web-api creating default aggregation profile..." ) + url = f"https://{self.config.web_api_endpoint}/api/v2/aggregation_profiles" + headers = { + "x-api-key": tenant_access_token, + "Accept": "application/json", + } + try: + response = requests.post( + url, json=payload, headers=headers, timeout=REQUEST_TIMEOUT + ) + response.raise_for_status() + logger.info( + f"tenant: {tenant_name} ({tenant_id}) - web-api aggregation profile created" + ) + return response.json()["data"]["id"] + + except requests.exceptions.HTTPError as e: + if e.response.status_code == 409: + logger.warning( + f"tenant: {tenant_name} ({tenant_id}) - web-api aggregation profile already exists" + ) + return + else: + raise + + def create_default_report( + self, + tenant_id: str, + tenant_name: str, + tenant_access_token: str, + payload: object, + ): + """Http call to web-api to create report""" + logger.debug( + f"tenant: {tenant_name} ({tenant_id}) - web-api creating default report..." + ) + + url = f"https://{self.config.web_api_endpoint}/api/v2/reports" + headers = { + "x-api-key": tenant_access_token, + "Accept": "application/json", + } + try: + response = requests.post( + url, json=payload, headers=headers, timeout=REQUEST_TIMEOUT + ) + response.raise_for_status() + logger.info( + f"tenant: {tenant_name} ({tenant_id}) - web-api default report created" + ) + return response.json()["data"]["id"] + + except requests.exceptions.HTTPError as e: + if e.response.status_code == 409: + logger.warning( + f"tenant: {tenant_name} ({tenant_id}) - web-api default report already exists" + ) + return + else: + raise + + def create_topology_service_types( + self, + tenant_id: str, + tenant_name: str, + tenant_access_token: str, + payload: object, + ): + """Http call to web-api to create service types""" + logger.debug( + f"tenant: {tenant_name} ({tenant_id}) - web-api creating default service-types..." + ) + + url = f"https://{self.config.web_api_endpoint}/api/v2/topology/service-types" + headers = { + "x-api-key": tenant_access_token, + "Accept": "application/json", + } + try: + response = requests.post( + url, json=payload, headers=headers, timeout=REQUEST_TIMEOUT + ) + response.raise_for_status() + logger.info( + f"tenant: {tenant_name} ({tenant_id}) - web-api topology service-types created" + ) + + except requests.exceptions.HTTPError as e: + if e.response.status_code == 409: + logger.warning( + f"tenant: {tenant_name} ({tenant_id}) - web-api topology service-types already exist for specific date" + ) + return + else: + raise + + def update_ready_state( self, tenant_id: str, diff --git a/automation/default.agg.json b/automation/default.agg.json new file mode 100644 index 00000000..e4f4b317 --- /dev/null +++ b/automation/default.agg.json @@ -0,0 +1,31 @@ +{ + "name": "default_aggregation", + "namespace": "", + "endpoint_group": "SERVICEGROUPS", + "metric_operation": "AND", + "profile_operation": "AND", + "metric_profile": { + "name": "default_metric", + "id": "" + }, + "groups": [ + { + "name": "services", + "operation": "AND", + "services": [ + { + "name": "iam", + "operation": "OR" + }, + { + "name": "webportal", + "operation": "OR" + }, + { + "name": "api", + "operation": "OR" + } + ] + } + ] +} \ No newline at end of file diff --git a/automation/default.metric.json b/automation/default.metric.json new file mode 100644 index 00000000..07a6f471 --- /dev/null +++ b/automation/default.metric.json @@ -0,0 +1,27 @@ +{ + "name": "default_metric", + "description": "Default metric profile", + "services": [ + { + "service": "api", + "metrics": [ + "generic.certificate.validity", + "generic.http.connect" + ] + }, + { + "service": "webportal", + "metrics": [ + "generic.certificate.validity", + "generic.http.connect" + ] + }, + { + "service": "iam", + "metrics": [ + "generic.certificate.validity", + "generic.http.connect" + ] + } + ] +} \ No newline at end of file diff --git a/automation/default.report.json b/automation/default.report.json new file mode 100644 index 00000000..83e25aa5 --- /dev/null +++ b/automation/default.report.json @@ -0,0 +1,33 @@ +{ + "disabled": false, + "info": { + "name": "Default", + "description": "Default A/R Report" + }, + "computations": { + "ar": true, + "status": true, + "trends": [ + "flapping", + "status", + "tags" + ] + }, + "thresholds": { + "availability": 80, + "reliability": 90, + "uptime": 0.8, + "unknown": 0.1, + "downtime": 0.1 + }, + "topology_schema": { + "group": { + "type": "PROJECT", + "group": { + "type": "SERVICEGROUPS" + } + } + }, + "profiles": [], + "filter_tags": [] +} \ No newline at end of file diff --git a/automation/default.services.json b/automation/default.services.json new file mode 100644 index 00000000..d8e20702 --- /dev/null +++ b/automation/default.services.json @@ -0,0 +1,26 @@ +[ + { + "name": "api", + "title": "API", + "description": "A generic rest api service accessible through http protocol", + "tags": [ + "topology" + ] + }, + { + "name": "iam", + "title": "Identity Management", + "description": "A generic identity management service", + "tags": [ + "topology" + ] + }, + { + "name": "webportal", + "title": "Webportal", + "description": "A generic web service accessible through http protocol", + "tags": [ + "topology" + ] + } +] \ No newline at end of file diff --git a/automation/init_compute_engine.py b/automation/init_compute_engine.py index cb1f97e4..0a07906c 100644 --- a/automation/init_compute_engine.py +++ b/automation/init_compute_engine.py @@ -61,9 +61,51 @@ def init_compute_engine( config.set_tenant_web_api_access(tenant_id, tenant_name, engine_user_key) config.save() + ops_id = None + metric_id = None + agg_id = None + with open(config.default_ops_profile_file, "r") as f: - payload = json.load(f) - web_api.create_ops_profile(tenant_id, tenant_name, engine_user_key, payload) + ops_payload = json.load(f) + ops_id = web_api.create_ops_profile( + tenant_id, tenant_name, engine_user_key, ops_payload + ) + + with open(config.default_metric_profile_file, "r") as f: + + metric_payload = json.load(f) + metric_id = web_api.create_metric_profile( + tenant_id, tenant_name, engine_user_key, metric_payload + ) + + with open(config.default_agg_profile_file, "r") as f: + + agg_payload = json.load(f) + agg_payload["namespace"] = tenant_name + agg_payload["metric_profile"]["id"] = metric_id + agg_id = web_api.create_aggregation_profile( + tenant_id, tenant_name, engine_user_key, agg_payload + ) + + with open(config.default_report_file, "r") as f: + + report_payload = json.load(f) + profiles = [ + {"id": ops_id, "type": "operations"}, + {"id": metric_id, "type": "metric"}, + {"id": agg_id, "type": "aggregation"}, + ] + report_payload["profiles"] = profiles + web_api.create_default_report( + tenant_id, tenant_name, engine_user_key, report_payload + ) + + with open(config.default_services_file, "r") as f: + + services_payload = json.load(f) + web_api.create_topology_service_types( + tenant_id, tenant_name, engine_user_key, services_payload + ) return True