initial commit
This commit is contained in:
@@ -0,0 +1,46 @@
|
||||
import allure
|
||||
from selenium.webdriver.remote.webelement import WebElement
|
||||
|
||||
|
||||
class CustomWebElement:
|
||||
"""Custom web element with allure logging."""
|
||||
|
||||
def __init__(self, by: str, locator: str, element: WebElement, description: str = None):
|
||||
self.by = by
|
||||
self.locator = locator
|
||||
self.element = element
|
||||
self.description = f"«{description}»" if description else "element"
|
||||
|
||||
def _execute_action(self, action, step):
|
||||
"""Execute action with allure logging.
|
||||
|
||||
:param action: Function to execute. Click, send_keys, etc
|
||||
:param step: Step description.
|
||||
"""
|
||||
@allure.step(step)
|
||||
def execute_action(locator_type=self.by, locator=self.locator):
|
||||
"""All arguments will be available in report."""
|
||||
return action()
|
||||
|
||||
return execute_action()
|
||||
|
||||
def click(self):
|
||||
self._execute_action(self.element.click,
|
||||
f"Click at {self.description}")
|
||||
|
||||
def send_keys(self, *value):
|
||||
self._execute_action(lambda: self.element.send_keys(*value),
|
||||
f"Send text {[v for v in value]} to {self.description}")
|
||||
|
||||
def __eq__(self, element):
|
||||
return self.element.__eq__(element)
|
||||
|
||||
def __ne__(self, element):
|
||||
return self.element.__ne__(element)
|
||||
|
||||
def __hash__(self):
|
||||
return self.element.__hash__()
|
||||
|
||||
def __getattr__(self, item):
|
||||
"""Missing methods will be executed from WebElement."""
|
||||
return getattr(self.element, item)
|
||||
@@ -0,0 +1,42 @@
|
||||
from selenium.webdriver import Remote
|
||||
from selenium.webdriver.common import by as selenium_by
|
||||
from screenshot_tests.page_objects.custom_web_element import CustomWebElement
|
||||
from typing import Union, TypeVar, Type
|
||||
|
||||
Locators = selenium_by.By
|
||||
|
||||
|
||||
class Page:
|
||||
"""Base page for all pages in PO."""
|
||||
|
||||
path = None
|
||||
|
||||
def __init__(self, driver: Remote):
|
||||
self.driver = driver
|
||||
|
||||
|
||||
PageBoundGeneric = TypeVar("PageBoundGeneric", bound=Page)
|
||||
|
||||
|
||||
class Element:
|
||||
"""Element descriptor for WebElement lazy init."""
|
||||
|
||||
def __init__(self, by: str, locator: str, description: str):
|
||||
self.by = by
|
||||
self.locator = locator
|
||||
self.description = description
|
||||
|
||||
def __get__(self,
|
||||
instance: PageBoundGeneric,
|
||||
owner: Type[PageBoundGeneric]) -> Union[CustomWebElement, 'Element']:
|
||||
"""
|
||||
https://docs.python.org/3/howto/descriptor.html
|
||||
:param instance: instance of owner
|
||||
:param owner: type of owner
|
||||
:return: self or WebElement instance
|
||||
"""
|
||||
if isinstance(instance, Element):
|
||||
return self
|
||||
|
||||
return CustomWebElement(self.by, self.locator, instance.driver.find_element(self.by, self.locator),
|
||||
self.description)
|
||||
@@ -0,0 +1,11 @@
|
||||
from screenshot_tests.page_objects.elements import Page, Element, Locators
|
||||
|
||||
|
||||
class YandexMainPage(Page):
|
||||
"""https://yandex.ru"""
|
||||
|
||||
path = ""
|
||||
|
||||
news_header = Element(Locators.CSS_SELECTOR, ".news__header", "Хэдер с новостями")
|
||||
search_field = Element(Locators.CSS_SELECTOR, ".search2", "Поисковый блок")
|
||||
search_input = Element(Locators.CSS_SELECTOR, ".input__control", "Поисковый инпут")
|
||||
Reference in New Issue
Block a user