From 217a3bce0996c4937d7c4bcd669cdf57343a47c0 Mon Sep 17 00:00:00 2001 From: tomdds Date: Wed, 13 Nov 2019 17:10:21 -0500 Subject: [PATCH] Basic load test file to query and create portfolios, apps and environments --- tests/locustfile.py | 158 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 158 insertions(+) create mode 100644 tests/locustfile.py diff --git a/tests/locustfile.py b/tests/locustfile.py new file mode 100644 index 00000000..b50114a4 --- /dev/null +++ b/tests/locustfile.py @@ -0,0 +1,158 @@ +import os +from random import choice, choices, randint +from urllib.parse import urlparse + +from locust import HttpLocust, TaskSequence, seq_task + +from pyquery import PyQuery as pq + +username = os.getenv("ATAT_BA_USERNAME", "") +password = os.getenv("ATAT_BA_PASSWORD", "") + +LETTERS = "qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM1234567890" + + +def login(l): + l.client.get("/login-dev", auth=(username, password)) + + +def logout(l): + l.client.get("/logout") + + +def get_index(l): + l.client.get("/") + + +def get_portfolios(l): + response = l.client.get("/portfolios") + d = pq(response.text) + portfolio_links = [ + p.attr("href") + for p in d( + ".global-panel-container .atat-table tbody tr td:first-child a" + ).items() + ] + force_new_portfolio = randint(0, 10) > 9 + if len(portfolio_links) == 0 or force_new_portfolio: + portfolio_links += [create_portfolio(l)] + + l.locust.portfolio_links = portfolio_links + + +def get_portfolio(l): + portfolio_link = choice(l.locust.portfolio_links) + response = l.client.get(portfolio_link) + d = pq(response.text) + application_links = [ + p.attr("href") + for p in d(".application-list .accordion__actions a:first-child").items() + ] + if len(application_links) > 0: + portfolio_id = portfolio_link.split("/")[-2] + update_app_registry(l, portfolio_id, application_links) + + +def update_app_registry(l, portfolio_id, app_links): + if not hasattr(l.locust, "app_links"): + l.locust.app_links = {} + l.locust.app_links[portfolio_id] = app_links + + +def get_app(l): + app_link = pick_app(l) + force_new_app = randint(0, 10) > 9 + if app_link is not None and not force_new_app: + l.client.get(app_link) + else: + portfolio_id = choice(l.locust.portfolio_links).split("/")[-2] + update_app_registry(l, portfolio_id, create_new_app(l, portfolio_id)) + + +def pick_app(l): + if hasattr(l.locust, "app_links") and len(l.locust.app_links.items()) > 0: + return choice(choice(list(l.locust.app_links.values()))) + + +def create_new_app(l, portfolio_id): + create_app_body = { + "name": f"Load Test Created - {''.join(choices(LETTERS, k=5))}", + "description": "Description", + } + + create_app_url = f"/portfolios/{portfolio_id}/applications/new" + + create_app_response = l.client.post(create_app_url, create_app_body) + + application_id = create_app_response.url.split("/")[-3] + + create_environments_body = { + "environment_names-0": "Development", + "environment_names-1": "Testing", + "environment_names-2": "Staging", + "environment_names-3": "Production", + } + + create_environments_url = ( + f"/applications/{application_id}/new/step_2?portfolio_id={portfolio_id}" + ) + + l.client.post(create_environments_url, create_environments_body) + + return f"/applications/{application_id}/settings" + + +def create_portfolio(l): + new_portfolio_body = { + "name": f"Load Test Created - {''.join(choices(LETTERS, k=5))}", + "defense_component": "Army, Department of the", + "description": "Test", + "app_migration": "none", + "native_apps": "yes", + "complexity": "storage", + "complexity_other": "", + "dev_team": "civilians", + "dev_team_other": "", + "team_experience": "none", + } + + response = l.client.post("/portfolios", new_portfolio_body) + + return urlparse(response.url).path + + +class UserBehavior(TaskSequence): + def on_start(self): + self.client.verify = False + login(self) + + @seq_task(1) + def home(l): + get_index(l) + + @seq_task(2) + def portfolios(l): + get_portfolios(l) + + @seq_task(3) + def pick_a_portfolio(l): + get_portfolio(l) + + @seq_task(4) + def pick_an_app(l): + get_app(l) + + def on_stop(self): + logout(self) + + +class WebsiteUser(HttpLocust): + task_set = UserBehavior + min_wait = 3000 + max_wait = 9000 + + +if __name__ == "__main__": + # if run as the main file, will spin up a single locust + # and run through the sequence as it + WebsiteUser().run()