-
Notifications
You must be signed in to change notification settings - Fork 8
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #110 from lsst-sqre/tickets/DM-26751
[DM-26751] Add Selenium tests
- Loading branch information
Showing
14 changed files
with
308 additions
and
37 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
"""Base page model for Selenium tests.""" | ||
|
||
from __future__ import annotations | ||
|
||
from typing import TYPE_CHECKING | ||
|
||
if TYPE_CHECKING: | ||
from typing import List, Union | ||
|
||
from selenium.webdriver.remote.webelement import WebElement | ||
from seleniumwire import webdriver | ||
|
||
|
||
class BaseFinder: | ||
def __init__(self, root: Union[webdriver.Chrome, WebElement]) -> None: | ||
self.root = root | ||
|
||
def find_element_by_class_name(self, name: str) -> WebElement: | ||
return self.root.find_element_by_class_name(name) | ||
|
||
def find_elements_by_class_name(self, name: str) -> List[WebElement]: | ||
return self.root.find_elements_by_class_name(name) | ||
|
||
def find_element_by_id(self, id_: str) -> WebElement: | ||
return self.root.find_element_by_id(id_) | ||
|
||
|
||
class BasePage(BaseFinder): | ||
def __init__(self, root: webdriver.Chrome) -> None: | ||
self.root = root | ||
|
||
@property | ||
def page_source(self) -> str: | ||
return self.root.page_source | ||
|
||
|
||
class BaseElement(BaseFinder): | ||
def __init__(self, root: WebElement) -> None: | ||
self.root = root |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,84 @@ | ||
"""Page models for token-related pages.""" | ||
|
||
from __future__ import annotations | ||
|
||
import re | ||
from typing import TYPE_CHECKING | ||
|
||
from tests.pages.base import BaseElement, BasePage | ||
from tests.support.selenium import run | ||
|
||
if TYPE_CHECKING: | ||
from typing import List, Optional | ||
|
||
from selenium.webdriver.remote.webelement import WebElement | ||
|
||
|
||
class NewTokenPage(BasePage): | ||
@property | ||
def form(self) -> WebElement: | ||
return self.find_element_by_id("create-token") | ||
|
||
@property | ||
def scopes(self) -> List[ScopeRow]: | ||
return [ | ||
ScopeRow(e) | ||
for e in self.find_elements_by_class_name("qa-token-scope") | ||
] | ||
|
||
async def submit(self) -> None: | ||
button = self.form.find_element_by_id("submit") | ||
await run(button.click) | ||
|
||
|
||
class TokensPage(BasePage): | ||
@property | ||
def new_token(self) -> Optional[str]: | ||
alert = self.find_elements_by_class_name("alert") | ||
if not alert: | ||
return None | ||
match = re.search("Token: ([^ ]+)", alert[0].text) | ||
if match: | ||
return match.group(1) | ||
else: | ||
return None | ||
|
||
@property | ||
def tokens(self) -> List[TokenRow]: | ||
return [ | ||
TokenRow(e) | ||
for e in self.find_elements_by_class_name("qa-token-row") | ||
] | ||
|
||
async def click_create_token(self) -> None: | ||
button = self.find_element_by_id("new-token") | ||
await run(button.click) | ||
|
||
|
||
class ScopeRow(BaseElement): | ||
@property | ||
def checkbox(self) -> WebElement: | ||
return self.find_element_by_class_name("form-check-input") | ||
|
||
@property | ||
def description(self) -> str: | ||
return self.find_element_by_class_name("qa-scope-description").text | ||
|
||
@property | ||
def label(self) -> str: | ||
return self.find_element_by_class_name("form-check-label").text | ||
|
||
|
||
class TokenRow(BaseElement): | ||
@property | ||
def key(self) -> str: | ||
return self.find_element_by_class_name("token-link").text | ||
|
||
@property | ||
def link(self) -> str: | ||
token_link = self.find_element_by_class_name("token-link") | ||
return token_link.find_element_by_tag_name("a").get_attribute("href") | ||
|
||
@property | ||
def scope(self) -> str: | ||
return self.find_element_by_class_name("qa-token-scope").text |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
"""Selenium tests for ``/auth/tokens``.""" | ||
|
||
from __future__ import annotations | ||
|
||
from typing import TYPE_CHECKING | ||
|
||
from gafaelfawr.session import SessionHandle | ||
from tests.pages.tokens import NewTokenPage, TokensPage | ||
from tests.support.selenium import run | ||
|
||
if TYPE_CHECKING: | ||
from seleniumwire import webdriver | ||
|
||
from tests.setup import SetupTestCallable | ||
|
||
|
||
async def test_create_token( | ||
create_test_setup: SetupTestCallable, driver: webdriver.Chrome | ||
) -> None: | ||
setup = await create_test_setup() | ||
token = setup.create_token(scope="read:all") | ||
driver.header_overrides = {"X-Auth-Request-Token": token.encoded} | ||
|
||
tokens_url = str(setup.client.make_url("/auth/tokens")) | ||
await run(lambda: driver.get(tokens_url)) | ||
|
||
tokens_page = TokensPage(driver) | ||
assert tokens_page.tokens == [] | ||
await tokens_page.click_create_token() | ||
|
||
new_tokens_page = NewTokenPage(driver) | ||
assert len(new_tokens_page.scopes) == 1 | ||
scope = new_tokens_page.scopes[0] | ||
assert scope.label == "read:all" | ||
assert scope.description == "can read everything" | ||
assert not scope.checkbox.is_selected() | ||
scope.checkbox.click() | ||
await new_tokens_page.submit() | ||
|
||
tokens_page = TokensPage(driver) | ||
assert tokens_page.new_token | ||
session_handle = SessionHandle.from_str(tokens_page.new_token) | ||
assert len(tokens_page.tokens) == 1 | ||
token_row = tokens_page.tokens[0] | ||
assert token_row.key == session_handle.key | ||
assert token_row.link.endswith(f"/auth/tokens/{session_handle.key}") | ||
assert token_row.scope == "read:all" |
Oops, something went wrong.