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()
예제 #3
0
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)
예제 #4
0
    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)
예제 #5
0
    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)
예제 #6
0
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",
예제 #7
0
    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)
예제 #8
0
 def __init__(self, arguments):
     self.args = arguments
     self.data_manager = DataManager(arguments, arguments["galloper_url"],
                                     arguments["token"],
                                     arguments["project_id"])
     self.report_builder = ReportBuilder()