def __init__(self, arguments): self.args = arguments self.data_manager = DataManager(arguments) self.report_builder = ReportBuilder() self.smtp_config = { 'host': arguments['smpt_host'], 'port': arguments['smpt_port'], 'user': arguments['smpt_user'], 'password': arguments['smpt_password'] }
class EmailNotification: def __init__(self, arguments): self.args = arguments self.data_manager = DataManager(arguments) self.report_builder = ReportBuilder() self.smtp_config = { 'host': arguments['smpt_host'], 'port': arguments['smpt_port'], 'user': arguments['smpt_user'], 'password': arguments['smpt_password'] } def email_notification(self): tests_data, last_test_data, baseline, violation, compare_with_thresholds = self.data_manager.get_api_test_info( ) email_body, charts, date = self.report_builder.create_api_email_body( tests_data, last_test_data, baseline, self.args['comparison_metric'], violation, compare_with_thresholds) self.send_email(self.smtp_config, self.args['user_list'], email_body, charts, date) def ui_email_notification(self): tests_data, last_test_data = self.data_manager.get_ui_test_info() email_body, charts, date = self.report_builder.create_ui_email_body( tests_data, last_test_data) self.send_email(self.smtp_config, self.args['user_list'], email_body, charts, date) def send_email(self, smtp_config, user_list, email_body, charts, date): s = smtplib.SMTP_SSL(host=smtp_config['host'], port=int(smtp_config['port'])) s.ehlo() s.login(smtp_config['user'], smtp_config['password']) subject = "[" + str(self.args['notification_type']) + "] " subject += "Test results for \"" + str(self.args['test']) subject += "\". Users count: " + str( self.args['users']) + ". From " + str(date) + "." for user in user_list: if all(i in user for i in ["<mailto:", "|"]): user = user.split("|")[1].replace(">", "").replace("<", "") msg_root = MIMEMultipart('related') msg_root['Subject'] = subject msg_root['From'] = smtp_config['user'] msg_root['To'] = user msg_alternative = MIMEMultipart('alternative') msg_alternative.attach(MIMEText(email_body, 'html')) msg_root.attach(msg_alternative) for chart in charts: msg_root.attach(chart) s.sendmail(smtp_config['user'], user, msg_root.as_string()) s.quit()
class ApiEmailNotification: def __init__(self, arguments): self.args = arguments self.data_manager = DataManager(arguments, arguments["galloper_url"], arguments["token"], arguments["project_id"]) self.report_builder = ReportBuilder() def email_notification(self): tests_data, last_test_data, baseline, violation, compare_with_thresholds = self.data_manager.get_api_test_info( ) email_body, charts, date = self.report_builder.create_api_email_body( self.args, tests_data, last_test_data, baseline, self.args['comparison_metric'], violation, compare_with_thresholds) subject = "[" + str(self.args['notification_type']) + "] " subject += "Test results for \"" + str(self.args['test']) subject += "\". Users count: " + str( self.args['users']) + ". From " + str(date) + "." return Email(self.args['test'], subject, self.args['user_list'], email_body, charts, date)
def post_processing(self, args, aggregated_errors, galloper_url=None): junit_report = environ.get("junit_report") data_manager = DataManager(args) if self.config_file: with open("/tmp/config.yaml", "w") as f: f.write(self.config_file) if not galloper_url: galloper_url = environ.get("galloper_url") reporter = Reporter() rp_service, jira_service = reporter.parse_config_file(args) performance_degradation_rate, missed_threshold_rate = 0, 0 compare_with_baseline, compare_with_thresholds = [], [] if args['influx_host']: data_manager.write_comparison_data_to_influx() performance_degradation_rate, compare_with_baseline = data_manager.compare_with_baseline( ) missed_threshold_rate, compare_with_thresholds = data_manager.compare_with_thresholds( ) reporter.report_performance_degradation( performance_degradation_rate, compare_with_baseline, rp_service, jira_service) reporter.report_missed_thresholds(missed_threshold_rate, compare_with_thresholds, rp_service, jira_service) r = requests.get( f'{galloper_url}/report/create?build_id={args["build_id"]}&lg_type={args["influx_db"]}&test_name={args["simulation"]}' ) print(r.text) print(r.content) reporter.report_errors(aggregated_errors, rp_service, jira_service, performance_degradation_rate, compare_with_baseline, missed_threshold_rate, compare_with_thresholds) if junit_report: parser = JTLParser() results = parser.parse_jtl() aggregated_requests = results['requests'] thresholds = self.calculate_thresholds(results) JUnit_reporter.process_report(aggregated_requests, thresholds)
def post_processing(self, args, aggregated_errors, galloper_url=None, project_id=None, junit_report=False, results_bucket=None, prefix=None, token=None, integration=[], email_recipients=None): if not galloper_url: galloper_url = environ.get("galloper_url") if not project_id: project_id = environ.get("project_id") if not token: token = environ.get("token") headers = {'Authorization': f'bearer {token}'} if token else {} status = "" try: if galloper_url and project_id and args.get("build_id"): url = f'{galloper_url}/api/v1/reports/{project_id}/processing?build_id={args.get("build_id")}' r = requests.get(url, headers={ **headers, 'Content-type': 'application/json' }).json() status = r["test_status"]["status"] if status == "Finished": print("Post processing has already finished") raise Exception("Post processing has already finished") except: print("Failed to check test status") start_post_processing = time() if not junit_report: junit_report = environ.get("junit_report") data_manager = DataManager(args, galloper_url, token, project_id) if self.config_file: with open("/tmp/config.yaml", "w") as f: f.write(self.config_file) reporter = Reporter() rp_service, jira_service = reporter.parse_config_file(args) ado_reporter = None if not jira_service and "jira" in integration: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: jira_core_config = loads( requests.get(secrets_url + "jira", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): jira_core_config = {} try: jira_additional_config = loads( requests.get(secrets_url + "jira_perf_api", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): jira_additional_config = {} jira_service = reporter.get_jira_service( args, jira_core_config, jira_additional_config) if not rp_service and "report_portal" in integration: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: rp_core_config = loads( requests.get(secrets_url + "rp", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): rp_core_config = {} try: rp_additional_config = loads( requests.get(secrets_url + "rp_perf_api", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): rp_additional_config = {} rp_service = reporter.get_rp_service(args, rp_core_config, rp_additional_config) if "azure_devops" in integration: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: ado_config = loads( requests.get(secrets_url + "ado", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): ado_config = {} if ado_config: ado_reporter = ADOReporter(ado_config, args) performance_degradation_rate, missed_threshold_rate = 0, 0 users_count, duration = 0, 0 total_checked_thresholds = 0 response_times = {} compare_with_baseline, compare_with_thresholds = [], [] if args['influx_host']: try: users_count, duration, response_times = data_manager.write_comparison_data_to_influx( ) except Exception as e: print("Failed to aggregate results") print(e) try: performance_degradation_rate, compare_with_baseline = data_manager.compare_with_baseline( ) except Exception as e: print("Failed to compare with baseline") print(e) try: total_checked_thresholds, missed_threshold_rate, compare_with_thresholds = data_manager.compare_with_thresholds( ) except Exception as e: print("Failed to compare with thresholds") print(e) try: reporter.report_performance_degradation( performance_degradation_rate, compare_with_baseline, rp_service, jira_service, ado_reporter) reporter.report_missed_thresholds(missed_threshold_rate, compare_with_thresholds, rp_service, jira_service, ado_reporter) except Exception as e: print(e) if junit_report: try: last_build = data_manager.get_last_build() total_checked, violations, thresholds = data_manager.get_thresholds( last_build, True) report = JUnit_reporter.create_report(thresholds, prefix) files = {'file': open(report, 'rb')} if project_id: upload_url = f'{galloper_url}/api/v1/artifact/{project_id}/{results_bucket}' else: upload_url = f'{galloper_url}/artifacts/{results_bucket}/upload' requests.post(upload_url, allow_redirects=True, files=files, headers=headers) junit_report = None except Exception as e: print("Failed to create junit report") print(e) if galloper_url: thresholds_quality_gate = environ.get( "thresholds_quality_gate", 20) try: thresholds_quality_gate = int(thresholds_quality_gate) except: thresholds_quality_gate = 20 if total_checked_thresholds: if missed_threshold_rate > thresholds_quality_gate: test_status = { "status": "Failed", "percentage": 100, "description": f"Missed more then {thresholds_quality_gate}% thresholds" } else: test_status = { "status": "Success", "percentage": 100, "description": f"Successfully met more than {100 - thresholds_quality_gate}% of thresholds" } else: test_status = { "status": "Finished", "percentage": 100, "description": "Test is finished" } lg_type = args["influx_db"].split( "_")[0] if "_" in args["influx_db"] else args["influx_db"] # TODO set status to failed or passed based on thresholds data = { 'build_id': args["build_id"], 'test_name': args["simulation"], 'lg_type': lg_type, 'missed': int(missed_threshold_rate), 'test_status': test_status, 'vusers': users_count, 'duration': duration, 'response_times': dumps(response_times) } if project_id: url = f'{galloper_url}/api/v1/reports/{project_id}' else: url = f'{galloper_url}/api/report' r = requests.put(url, json=data, headers={ **headers, 'Content-type': 'application/json' }) print(r.text) if r.json()["message"] == "updated" and self.str2bool( environ.get("remove_row_data")): data_manager.delete_test_data() try: reporter.report_errors(aggregated_errors, rp_service, jira_service, performance_degradation_rate, compare_with_baseline, missed_threshold_rate, compare_with_thresholds, ado_reporter) except Exception as e: print(e) print("Total time - %s seconds" % (round(time() - start_post_processing, 2))) if junit_report: parser = JTLParser() results = parser.parse_jtl() aggregated_requests = results['requests'] thresholds = self.calculate_thresholds(results) JUnit_reporter.process_report(aggregated_requests, thresholds) if "email" in integration and email_recipients: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: email_notification_id = requests.get( secrets_url + "email_notification_id", headers={ 'Authorization': f'bearer {token}', 'Content-type': 'application/json' }).json()["secret"] except (AttributeError, JSONDecodeError): email_notification_id = "" if email_notification_id: emails = [x.strip() for x in email_recipients.split(",")] task_url = f"{galloper_url}/api/v1/task/{project_id}/{email_notification_id}" event = { "influx_host": args["influx_host"], "influx_port": args["influx_port"], "influx_user": args["influx_user"], "influx_password": args["influx_password"], "influx_db": args['influx_db'], "comparison_db": args['comparison_db'], "test": args['simulation'], "user_list": emails, "notification_type": "api", "test_type": args["type"], "env": args["env"], "users": users_count } res = requests.post(task_url, json=event, headers={ 'Authorization': f'bearer {token}', 'Content-type': 'application/json' }) print("Email notification") print(res.text)
import pytest import requests_mock import os from perfreporter.data_manager import DataManager import tests.utils.constants as c from perfreporter.junit_reporter import JUnit_reporter galloper_url = "http://example" token = "test" project_id = 1 data_manager = DataManager(c.ARGS, galloper_url, token, project_id) def test_compare_with_baseline(): performance_degradation_rate, compare_with_baseline = data_manager.compare_with_baseline( c.BASELINE, c.TEST_DATA) print(performance_degradation_rate) print(compare_with_baseline) failed_requests = [] for each in compare_with_baseline: failed_requests.append(each["request_name"]) assert performance_degradation_rate == 62.5 assert all(req in ['Step1', 'Step2', 'Step3', 'Step4', 'Step5_Get_Code'] for req in failed_requests) def test_get_thresholds_and_create_junit_report(): with requests_mock.Mocker() as mock: mock.get( f"{galloper_url}/api/v1/thresholds/{project_id}/backend?name={c.ARGS['simulation']}&" f"environment={c.ARGS['env']}&order=asc",
def post_processing(self, args, aggregated_errors, galloper_url=None, project_id=None, junit_report=False, results_bucket=None, prefix=None, token=None, integration=[], email_recipients=None): if not junit_report: junit_report = environ.get("junit_report") data_manager = DataManager(args) if self.config_file: with open("/tmp/config.yaml", "w") as f: f.write(self.config_file) if not galloper_url: galloper_url = environ.get("galloper_url") if not project_id: project_id = environ.get("project_id") if not token: token = environ.get("token") headers = {'Authorization': f'bearer {token}'} if token else {} reporter = Reporter() rp_service, jira_service = reporter.parse_config_file(args) if not jira_service and "jira" in integration: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: jira_core_config = loads( requests.get(secrets_url + "jira", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): jira_core_config = {} try: jira_additional_config = loads( requests.get(secrets_url + "jira_perf_api", headers={ **headers, 'Content-type': 'application/json' }).json()["secret"]) except (AttributeError, JSONDecodeError): jira_additional_config = {} jira_service = reporter.get_jira_service( args, jira_core_config, jira_additional_config) performance_degradation_rate, missed_threshold_rate = 0, 0 compare_with_baseline, compare_with_thresholds = [], [] if args['influx_host']: data_manager.write_comparison_data_to_influx() performance_degradation_rate, compare_with_baseline = data_manager.compare_with_baseline( ) missed_threshold_rate, compare_with_thresholds = data_manager.compare_with_thresholds( ) reporter.report_performance_degradation( performance_degradation_rate, compare_with_baseline, rp_service, jira_service) reporter.report_missed_thresholds(missed_threshold_rate, compare_with_thresholds, rp_service, jira_service) if junit_report: last_build = data_manager.get_last_build() violations, thresholds = data_manager.get_thresholds( last_build, True) report = JUnit_reporter.create_report(thresholds, prefix) files = {'file': open(report, 'rb')} if project_id: upload_url = f'{galloper_url}/api/v1/artifacts/{project_id}/{results_bucket}/file' else: upload_url = f'{galloper_url}/artifacts/{results_bucket}/upload' requests.post(upload_url, allow_redirects=True, files=files, headers=headers) junit_report = None if galloper_url: data = { 'build_id': args["build_id"], 'test_name': args["simulation"], 'lg_type': args["influx_db"], 'missed': int(missed_threshold_rate) } if project_id: url = f'{galloper_url}/api/v1/reports/{project_id}' else: url = f'{galloper_url}/api/report' r = requests.put(url, json=data, headers={ **headers, 'Content-type': 'application/json' }) print(r.text) reporter.report_errors(aggregated_errors, rp_service, jira_service, performance_degradation_rate, compare_with_baseline, missed_threshold_rate, compare_with_thresholds) if junit_report: parser = JTLParser() results = parser.parse_jtl() aggregated_requests = results['requests'] thresholds = self.calculate_thresholds(results) JUnit_reporter.process_report(aggregated_requests, thresholds) if "email" in integration and email_recipients: if galloper_url and token and project_id: secrets_url = f"{galloper_url}/api/v1/secrets/{project_id}/" try: email_notification_id = requests.get( secrets_url + "email_notification_id", headers={ 'Authorization': f'bearer {token}', 'Content-type': 'application/json' }).json()["secret"] except (AttributeError, JSONDecodeError): email_notification_id = "" if email_notification_id: emails = [x.strip() for x in email_recipients.split(",")] task_url = f"{galloper_url}/api/v1/task/{project_id}/{email_notification_id}" event = { "influx_host": args["influx_host"], "influx_port": args["influx_port"], "influx_user": args["influx_user"], "influx_password": args["influx_password"], "influx_db": args['influx_db'], "test": args['simulation'], "user_list": emails, "notification_type": "api", "test_type": args["type"], "users": data_manager.get_user_count() } print(event) res = requests.post(task_url, json=event, headers={ 'Authorization': f'bearer {token}', 'Content-type': 'application/json' }) print(res.text)
def __init__(self, arguments): self.args = arguments self.data_manager = DataManager(arguments, arguments["galloper_url"], arguments["token"], arguments["project_id"]) self.report_builder = ReportBuilder()