Merge pull request #6338 from emilghittasv/playwright-flakiness-try-fix

Playwright improve test stability
This commit is contained in:
Emil Ghitta 2024-11-07 11:13:27 +02:00 коммит произвёл GitHub
Родитель 99e0c88a9a 5dda7567da
Коммит 0e07070d27
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: B5690EEEBB952194
27 изменённых файлов: 402 добавлений и 182 удалений

Просмотреть файл

@ -118,47 +118,74 @@ class BasePage:
"""
return locator.all_text_contents()
def _checkbox_interaction(self, xpath: str, check: bool):
def _checkbox_interaction(self, element: [str, ElementHandle], check: bool, retries=3,
delay=2000):
"""
This helper function interacts with a checkbox element.
"""
if check:
self._get_element_locator(xpath).check()
else:
self._get_element_locator(xpath).uncheck()
def _click(self, element: Union[str, Locator], with_wait=True, with_force=False,
retries=3, delay=2000):
"""
This helper function clicks on a given element locator.
Args:
element (Union[str, ElementHandle]): The element locator to interact with.
check (bool): Whether to check or uncheck the checkbox.
"""
self.page.wait_for_load_state("networkidle")
for attempt in range(retries):
try:
if isinstance(element, str):
if with_wait:
self._wait_for_selector(element)
self._get_element_locator(element).click(force=with_force)
elif isinstance(element, Locator):
element.click(force=with_force)
print(f"Click succeeded on attempt {attempt + 1}")
locator = self._get_element_locator(element) if isinstance(
element,str) else element
if check:
locator.check()
else:
locator.uncheck()
break
except (PlaywrightTimeoutError, Exception) as error:
print(f"Click failed on attempt {attempt + 1}. Error: {error}")
except (PlaywrightTimeoutError, Exception) as e:
print(f"Checkbox interaction failed. Retrying... {e}")
if attempt < retries - 1:
self.page.wait_for_timeout(delay)
else:
raise Exception("Max retries exceeded. Could not perform the click")
raise Exception("Max retries exceeded. Could not interact with the checkbox")
def _click(self, element: Union[str, Locator, ElementHandle], expected_locator=None,
expected_url=None, with_force=False, retries=3, delay=2000):
"""
This helper function clicks on a given element locator.
Args:
element (Union[str, Locator, ElementHandle]): The element locator to click on.
expected_locator (str): The expected locator to wait for after the click.
expected_url (str): The expected URL to wait for after the click.
with_force (bool): Whether to force the click.
"""
self.page.wait_for_load_state("networkidle")
for attempt in range(retries):
try:
element_locator = self._get_element_locator(element) if isinstance(
element, str) else element
element_locator.click(force=with_force)
if expected_locator:
self.page.wait_for_selector(expected_locator, timeout=3000)
if expected_url:
self.page.wait_for_url(expected_url, timeout=3000)
break
except PlaywrightTimeoutError:
if expected_locator:
print(f"Expected locator {expected_locator} not found. Retrying...")
if expected_url:
print(f"Expected URL {expected_url} not found. Retrying...")
if attempt < retries - 1:
self.page.wait_for_timeout(delay)
def _click_on_an_element_by_index(self, xpath: str, index: int):
"""
This helper function clicks on a given element locator based on a given index.
"""
self.page.wait_for_load_state("networkidle")
self._get_element_locator(xpath).nth(index).click()
def _click_on_first_item(self, xpath: str):
"""
This helper function clicks on the first item from a given web element locator list.
"""
self.page.wait_for_load_state("networkidle")
self._get_element_locator(xpath).first.click()
def _fill(self, xpath: str, text: str):
@ -258,3 +285,13 @@ class BasePage:
self.page.wait_for_selector(xpath, timeout=timeout)
except PlaywrightTimeoutError:
print(f"{xpath} is not displayed")
def _move_mouse_to_location(self, x: int, y: int):
"""
This helper function moves the mouse to a given location.
Args:
x (int): The x-coordinate.
y (int): The y-coordinate.
"""
self.page.mouse.move(x, y)

Просмотреть файл

@ -1,4 +1,5 @@
import os
import warnings
import requests
import time
import re
@ -12,6 +13,7 @@ from playwright_tests.messages.homepage_messages import HomepageMessages
from requests.exceptions import HTTPError
from playwright_tests.pages.top_navbar import TopNavbar
from playwright_tests.test_data.search_synonym import SearchSynonyms
from playwright.sync_api import TimeoutError as PlaywrightTimeoutError
class Utilities:
@ -245,7 +247,7 @@ class Utilities:
"""
self.page.context.storage_state(path=f"core/sessions/.auth/{session_file_name}.json")
def delete_cookies(self, tried_once=False):
def delete_cookies(self, tried_once=False, retries=3):
"""
This helper function deletes all cookies and performs a page refresh so that the outcome
is visible immediately.
@ -254,8 +256,17 @@ class Utilities:
tried_once (bool): If the cookies deletion was tried once
"""
top_navbar = TopNavbar(self.page)
self.page.context.clear_cookies()
self.refresh_page()
for attempt in range(retries):
try:
self.page.context.clear_cookies()
self.refresh_page()
self.page.wait_for_selector(top_navbar.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS
["signin_signup_button"], timeout=3000)
break
except PlaywrightTimeoutError:
print("Cookies were not successfully deleted. Retrying...")
if attempt < retries - 1:
continue
# In order to avoid test flakiness we are trying to delete the cookies again if the sign-in
# sign-up button is not visible after page refresh.
@ -291,7 +302,7 @@ class Utilities:
"""
This helper function performs a page reload.
"""
self.page.reload()
self.page.reload(wait_until="networkidle")
def get_user_agent(self) -> str:
"""
@ -531,3 +542,24 @@ class Utilities:
This function blocks a certain request
"""
route.abort()
def re_call_function_on_error(self, func, *args, **kwargs):
"""This helper function re-calls a function if a 502 error is encountered.
Args:
func: The function to be re-called
*args: The function arguments
**kwargs: The function keyword arguments
"""
for attempt in range(3):
with warnings.catch_warnings(record=True) as w:
warnings.simplefilter("always")
func(*args, **kwargs)
if (any(issubclass(warning.category, UserWarning) and str(
warning.message) == "502 encountered" for warning in w)):
print("502 error encountered while executing the function. Retrying...")
if attempt < 2:
continue
break

Просмотреть файл

@ -20,8 +20,8 @@ class AAQFlow:
attach_image=False,
is_premium=False,
email="",
is_loginless=False
):
is_loginless=False,
expected_locator=None):
question_subject = ''
if is_premium:
self.add_valid_data_to_all_premium_products_aaq_fields(subject, body, is_loginless,
@ -34,7 +34,7 @@ class AAQFlow:
attach_image
)
# Submitting the question.
self.aaq_form_page.click_aaq_form_submit_button()
self.aaq_form_page.click_aaq_form_submit_button(expected_locator=expected_locator)
# If the submission was done for freemium products we are retrieving the Question Subject,
# Question url & Question Body for further test usage.

Просмотреть файл

@ -14,13 +14,15 @@ class MessagingSystemFlows:
def complete_send_message_form_with_data(self,
recipient_username='',
message_body='',
submit_message=True):
submit_message=True,
expected_url=None):
"""Complete the send message form with data.
Args:
recipient_username (str): The username of the recipient.
message_body (str): The body of the message.
submit_message (bool): Submit the message.
expected_url (str): The expected URL after the click event.
"""
if recipient_username:
if isinstance(recipient_username, list):
@ -35,13 +37,16 @@ class MessagingSystemFlows:
self.new_message_page.fill_into_new_message_body_textarea(message_body)
if submit_message:
self.new_message_page.click_on_new_message_send_button()
self.new_message_page.click_on_new_message_send_button(
expected_url=expected_url)
def delete_message_flow(self, username='',
excerpt='',
delete_message=True,
from_sent_list=False,
from_inbox_list=False):
from_inbox_list=False,
expected_url=None
):
"""Delete a message flow.
Args:
@ -50,6 +55,7 @@ class MessagingSystemFlows:
delete_message (bool): Delete the message.
from_sent_list (bool): Delete the message from the sent list.
from_inbox_list (bool): Delete the message from the inbox list
expected_url (str): The expected URL after the click event.
"""
if from_sent_list:
if username:
@ -64,4 +70,4 @@ class MessagingSystemFlows:
self.inbox_page.click_on_inbox_message_delete_button_by_excerpt(excerpt)
if delete_message:
self.sent_message_page.click_on_delete_page_delete_button()
self.sent_message_page.click_on_delete_page_delete_button(expected_url=expected_url)

Просмотреть файл

@ -19,7 +19,8 @@ class EditProfileDataFlow:
self.profile_contribution_areas = MyProfileEditContributionAreasPage(page)
# Editing a profile with data flow.
def edit_profile_with_test_data(self, info_only=False, submit_change=False) -> dict[str, str]:
def edit_profile_with_test_data(self, info_only=False, submit_change=False,
expected_url=None) -> dict[str, str]:
edit_test_data = self.utilities.profile_edit_test_data
valid_user_edit = edit_test_data["valid_user_edit"]
@ -50,7 +51,7 @@ class EditProfileDataFlow:
])
if submit_change:
self.edit_profile_page.click_update_my_profile_button()
self.edit_profile_page.click_update_my_profile_button(expected_url=expected_url)
return {
"username": valid_user_edit["username"],

Просмотреть файл

@ -22,4 +22,4 @@ class NewMessagePageMessages:
PREVIEW_MESSAGE_UL_LI_NUMBER_THREE = "Bulleted list item three"
PREVIEW_MESSAGE_EXTERNAL_LINK = "Test external link"
PREVIEW_MESSAGE_INTERNAL_LINK = "Test internal Link"
PREVIEW_MESSAGE_INTERNAL_LINK_TITLE = "Back up your Firefox data"
PREVIEW_MESSAGE_INTERNAL_LINK_TITLE = "DoNotDelete"

Просмотреть файл

@ -214,8 +214,8 @@ class AAQFormPage(BasePage):
def click_aaq_form_cancel_button(self):
self._click(self.__form_cancel_option)
def click_aaq_form_submit_button(self, with_force=False):
self._click(self.__form_submit_button, with_force)
def click_aaq_form_submit_button(self, expected_locator=None):
self._click(self.__form_submit_button, expected_locator=expected_locator)
# Edit question form actions.
def click_aaq_edit_submit_button(self):

Просмотреть файл

@ -25,10 +25,12 @@ class QuestionPage(BasePage):
__undo_solves_problem = "//input[@value='Undo']"
# Question locators.
__question_author = "//div[@class='question']//span[@class='display-name']"
__questions_header = "//h2[@class='sumo-callout-heading summary no-product-heading']"
__question_body = "//div[@class='main-content']/div/p"
__modified_question_section = "//p[@class='edited text-body-sm']"
QUESTION_LOCATORS = {
"question_author": "//div[@class='question']//span[@class='display-name']",
"questions_header": "//h2[@class='sumo-callout-heading summary no-product-heading']",
"question_body": "//div[@class='main-content']/div/p",
"modified_question_section": "//p[@class='edited text-body-sm']"
}
# Progress bar locators.
__complete_progress_items_label = ("//li[@class='progress--item is-complete']//span["
@ -212,25 +214,25 @@ class QuestionPage(BasePage):
# Page content actions.
def get_question_header(self) -> str:
return self._get_text_of_element(self.__questions_header)
return self._get_text_of_element(self.QUESTION_LOCATORS["questions_header"])
def click_last_reply_by(self):
self._click(self.__last_reply_by)
def get_question_body(self) -> str:
return self._get_text_of_element(self.__question_body)
return self._get_text_of_element(self.QUESTION_LOCATORS["question_body"])
def get_question_author_name(self) -> str:
return self._get_text_of_element(self.__question_author)
return self._get_text_of_element(self.QUESTION_LOCATORS["question_author"])
def get_question_id(self) -> str:
return self._get_element_attribute_value(self.__question_section, 'id')
def get_modified_question_locator(self) -> Locator:
return self._get_element_locator(self.__modified_question_section)
return self._get_element_locator(self.QUESTION_LOCATORS["modified_question_section"])
def get_modified_by_text(self) -> str:
return self._get_text_of_element(self.__modified_question_section)
return self._get_text_of_element(self.QUESTION_LOCATORS["modified_question_section"])
def get_add_image_section_locator(self) -> Locator:
return self._get_element_locator(self.__add_image_button)
@ -274,7 +276,7 @@ class QuestionPage(BasePage):
def add_text_to_add_a_tag_input_field(self, text: str):
self._fill(self.__add_a_tag_input_field, text)
self._click(f"//li[@class='ui-menu-item']/div[text()='{text}']")
self.page.click(f"//li[@class='ui-menu-item']/div[text()='{text}']")
def get_add_a_tag_input_field(self) -> Locator:
return self._get_element_locator(self.__add_a_tag_input_field)
@ -414,9 +416,9 @@ class QuestionPage(BasePage):
f"p[@class='edited text-body-sm']/em")
def click_on_post_reply_button(self, repliant_username) -> str:
self._click(self.__post_reply_button)
self._wait_for_selector(f"//span[@class='display-name' and contains"
f"(text(), '{repliant_username}')]")
self._click(self.__post_reply_button,
expected_locator=f"//span[@class='display-name' and contains(text(), "
f"'{repliant_username}')]")
return self._get_element_attribute_value(f"//span[@class='display-name' and "
f"contains(text(), '{repliant_username}')]/"
f"ancestor::div[@class='answer ']",
@ -551,7 +553,7 @@ class QuestionPage(BasePage):
return self._get_text_of_elements(self.__common_responses_responses_options)
def click_on_a_particular_category_option(self, option: str):
self._click(f"//ul[@class='category-list']/li[text()='{option}']", with_wait=True)
self._click(f"//ul[@class='category-list']/li[text()='{option}']")
def click_on_a_particular_response_option(self, option: str):
self._click(f"//ul[@class='sidebar-nav']/li[text()='{option}']")
@ -568,10 +570,10 @@ class QuestionPage(BasePage):
return self._get_text_of_element(self.__common_responses_response_preview)
def click_on_switch_to_mode(self):
self._click(self.__common_responses_switch_to_mode, with_wait=True)
self._click(self.__common_responses_switch_to_mode)
def click_on_common_responses_cancel_button(self):
self._click(self.__common_responses_cancel_button, with_wait=True)
self._click(self.__common_responses_cancel_button)
def click_on_common_responses_insert_response_button(self):
self._click(self.__common_responses_insert_response_button)

Просмотреть файл

@ -6,13 +6,13 @@ class KBArticleEditMetadata(BasePage):
# Edit article metadata page locators.
__edit_article_metadata_error = "//ul[@class='errorlist']"
__edit_article_metadata_page_header = "//h1[@class='sumo-page-heading']"
__restrict_visibility_input_field = "//input[@id='id_restrict_to_groups-selectized']"
__restrict_visibility_input_field = "//input[@id='id_restrict_to_groups-ts-control']"
__restricted_visibility_chosen_groups = (
"//input[@id='id_restrict_to_groups-selectized" "']/../div[@class='item']"
"//input[@id='id_restrict_to_groups-ts-control']/../div[@class='item']"
)
__clear_all_selected_groups_button = "//a[@class='clear']"
__kb_article_restrict_visibility_field = "//input[@id='id_restrict_to_groups-selectized']"
__kb_article_restrict_visibility_delete_all_groups = "//a[@title='Clear']"
__clear_all_selected_groups_button = "//div[@class='clear-button']"
__kb_article_restrict_visibility_field = "//input[@id='id_restrict_to_groups-ts-control']"
__kb_article_restrict_visibility_delete_all_groups = "//a[@title='remove']"
__title_input_field = "//input[@id='id_title']"
__slug_input_field = "//input[@id='id_slug']"
__category_select_field = "//select[@id='id_category']"
@ -42,6 +42,7 @@ class KBArticleEditMetadata(BasePage):
self._click(self.__clear_all_selected_groups_button)
def is_clear_all_restricted_visibility_group_selection_visible(self) -> bool:
self._hover_over_element(self.__restrict_visibility_input_field)
return self._is_element_visible(self.__clear_all_selected_groups_button)
def add_and_select_restrict_visibility_group_metadata(self, group_name: str):
@ -52,7 +53,7 @@ class KBArticleEditMetadata(BasePage):
if group_name != "":
self._click(f"//div[@class='item' and text()='{group_name}']/a")
else:
self._click(self.__kb_article_restrict_visibility_delete_all_groups)
self._click(self.__clear_all_selected_groups_button)
def get_text_of_title_input_field(self) -> str:
return self._get_element_input_value(self.__title_input_field)

Просмотреть файл

@ -5,8 +5,8 @@ from playwright_tests.core.basepage import BasePage
class SubmitKBArticlePage(BasePage):
__kb_article_for_contributors_sidebar = "//nav[@id='for-contributors-sidebar']"
# New KB article form locators.
__kb_article_restrict_visibility_field = "//input[@id='id_restrict_to_groups-selectized']"
__kb_article_restrict_visibility_delete_all_groups = "//a[@title='Clear']"
__kb_article_restrict_visibility_field = "//input[@id='id_restrict_to_groups-ts-control']"
__kb_article_restrict_visibility_delete_all_groups = "//div[@class='clear-button']"
__kb_article_form_title = "//input[@id='id_title']"
__kb_article_form_slug = "//input[@id='id_slug']"
__kb_article_category_select = "//select[@id='id_category']"

Просмотреть файл

@ -106,9 +106,14 @@ class InboxPage(BasePage):
"""Click on the mark selected as read button."""
self._click(self.INBOX_BUTTON_LOCATORS["inbox_mark_selected_as_read_button"])
def click_on_inbox_delete_selected_button(self):
"""Click on the delete selected button."""
self._click(self.INBOX_BUTTON_LOCATORS["inbox_delete_selected_button"])
def click_on_inbox_delete_selected_button(self, expected_locator=None):
"""Click on the delete selected button.
Args:
expected_locator: The expected locator after the click event.
"""
self._click(self.INBOX_BUTTON_LOCATORS["inbox_delete_selected_button"],
expected_locator=expected_locator)
def click_on_inbox_message_sender_username(self, username: str):
"""Click on the username of the message sender.
@ -140,9 +145,14 @@ class InboxPage(BasePage):
self._click((f"//div[@class='email-cell from']//a[contains(text(),'{username}')]/../.."
f"//a[@class='read']"))
def click_on_delete_page_delete_button(self):
"""Click on the delete button on the delete message page."""
self._click(self.INBOX_BUTTON_LOCATORS["inbox_delete_page_delete_button"])
def click_on_delete_page_delete_button(self, expected_url=None):
"""Click on the delete button on the delete message page.
Args:
expected_url: The expected URL after deleting the message.
"""
self._click(self.INBOX_BUTTON_LOCATORS["inbox_delete_page_delete_button"],
expected_url=expected_url)
def click_on_delete_page_cancel_button(self):
"""Click on the cancel button on the delete message page."""
@ -195,8 +205,12 @@ class InboxPage(BasePage):
return self._get_text_of_elements(self.INBOX_MESSAGES_LOCATORS
["all_read_messages_excerpt"])
def delete_all_inbox_messages(self):
"""Delete all the inbox messages."""
def delete_all_inbox_messages(self, expected_url=None):
"""Delete all the inbox messages.
Args:
expected_url: The expected URL after deleting all the messages.
"""
inbox_messages_count = self._get_element_handles(self.INBOX_MESSAGES_LOCATORS
["inbox_messages"])
for i in range(len(inbox_messages_count)):
@ -204,8 +218,8 @@ class InboxPage(BasePage):
self.INBOX_MESSAGES_LOCATORS["inbox_messages_delete_button"])
delete_button = inbox_elements_delete_button[i]
delete_button.click()
self.click_on_delete_page_delete_button()
self._click(delete_button)
self.click_on_delete_page_delete_button(expected_url=expected_url)
def check_a_particular_message(self, excerpt=''):
"""Check a particular message.
@ -216,11 +230,12 @@ class InboxPage(BasePage):
inbox_checkbox = self.inbox_message_select_checkbox_element(excerpt)
inbox_checkbox[0].check()
def delete_all_inbox_messages_via_delete_selected_button(self, excerpt=''):
def delete_all_inbox_messages_via_delete_selected_button(self, excerpt='', expected_url=None):
"""Delete all the inbox messages via the delete selected button.
Args:
excerpt: The excerpt of the message.
expected_url: The expected URL after deleting all the messages.
"""
if excerpt != '':
inbox_messages_count = self._inbox_message_element_handles(excerpt)
@ -234,11 +249,11 @@ class InboxPage(BasePage):
else:
inbox_checkbox = self.inbox_message_select_checkbox_element()
element = inbox_checkbox[counter]
element.click()
self._checkbox_interaction(element, True)
counter += 1
self.click_on_inbox_delete_selected_button()
self.click_on_delete_page_delete_button()
self.click_on_delete_page_delete_button(expected_url=expected_url)
def get_all_unread_messages(self) -> list[Locator]:
"""Get all the unread messages."""

Просмотреть файл

@ -126,9 +126,15 @@ class NewMessagePage(BasePage):
"""Click on the new message preview button."""
self._click(self.PREVIEW_SECTION_LOCATORS["new_message_preview_button"])
def click_on_new_message_send_button(self):
"""Click on the new message send button."""
self._click(self.NEW_MESSAGE_PAGE_LOCATORS["new_message_send_button"])
def click_on_new_message_send_button(self, expected_url=None):
"""Click on the new message send button.
Args:
expected_url (str): The expected URL after the click event.
"""
self._click(self.NEW_MESSAGE_PAGE_LOCATORS["new_message_send_button"],
expected_url=expected_url
)
def click_on_a_search_result(self, username: str):
"""Click on a search result.

Просмотреть файл

@ -58,9 +58,14 @@ class SentMessagePage(BasePage):
f"'{username}')]/../.."
f"/div[@class='email-cell excerpt']/a")
def click_on_delete_selected_button(self):
"""Click on the delete selected button on the sent messages page."""
self._click(self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_delete_selected_button"])
def click_on_delete_selected_button(self, expected_locator=None):
"""Click on the delete selected button on the sent messages page.
Args:
expected_locator (str): The expected locator after the click event.
"""
self._click(self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_delete_selected_button"],
expected_locator=expected_locator)
def click_on_sent_message_delete_button_by_user(self, username: str):
"""Click on the delete button of a sent message by the username of the recipient.
@ -117,9 +122,14 @@ class SentMessagePage(BasePage):
self._click(f"//div[@class='email-cell to-groups']/a[text()='{group_name}']/../../"
f"div[@class='email-cell excerpt']")
def click_on_delete_page_delete_button(self):
"""Click on the delete button on the delete message page."""
self._click(self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_delete_page_delete_button"])
def click_on_delete_page_delete_button(self, expected_url=None):
"""Click on the delete button on the delete message page.
Args:
expected_url (str): The expected URL after the deletion.
"""
self._click(self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_delete_page_delete_button"],
expected_url=expected_url)
def click_on_delete_page_cancel_button(self):
"""Click on the cancel button on the delete message page."""
@ -173,21 +183,26 @@ class SentMessagePage(BasePage):
"""Check if the sent messages are displayed."""
return self._is_element_visible(self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_section"])
def delete_all_displayed_sent_messages(self):
"""Delete all the displayed sent messages."""
def delete_all_displayed_sent_messages(self, expected_url=None):
"""Delete all the displayed sent messages.
Args:
expected_url (str): The expected URL after the deletion.
"""
sent_elements_delete_button = self._get_element_handles(
self.SENT_MESSAGE_PAGE_LOCATORS["sent_messages_delete_button"])
for i in range(len(sent_elements_delete_button)):
delete_button = sent_elements_delete_button[i]
delete_button.click()
self.click_on_delete_page_delete_button()
self._click(delete_button)
self.click_on_delete_page_delete_button(expected_url=expected_url)
def delete_all_sent_messages_via_delete_selected_button(self, excerpt=''):
def delete_all_sent_messages_via_delete_selected_button(self, excerpt='', expected_url=None):
"""Delete all the sent messages via the delete selected button.
Args:
excerpt (str): The excerpt of the message.
expected_url (str): The expected URL after the deletion.
"""
if excerpt != '':
sent_messages_count = self.sent_messages_by_excerpt_element_handles(excerpt)
@ -201,11 +216,11 @@ class SentMessagePage(BasePage):
else:
checkbox = self.sent_message_select_checkbox()
element = checkbox[counter]
element.click()
self._checkbox_interaction(element, True)
counter += 1
self.click_on_delete_selected_button()
self.click_on_delete_page_delete_button()
self.click_on_delete_page_delete_button(expected_url=expected_url)
# Read Sent Message page
def get_text_of_all_sent_groups(self) -> list[str]:

Просмотреть файл

@ -269,26 +269,41 @@ class TopNavbar(BasePage):
"""Click on the 'View Profile' option"""
self._hover_over_element(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_username"])
self._click(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_view_profile_option"])
# Sometimes the top-navbar is not hidden after clicking on the 'Settings' option. This
# action is to move the mouse to the top-left corner of the page to hide the top-navbar.
self._move_mouse_to_location(0, 0)
def click_on_edit_profile_option(self):
"""Click on the 'Edit Profile' option"""
self._hover_over_element(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_username"])
self._click(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_edit_profile_option"])
# Sometimes the top-navbar is not hidden after clicking on the 'Settings' option. This
# action is to move the mouse to the top-left corner of the page to hide the top-navbar.
self._move_mouse_to_location(0, 0)
def click_on_settings_profile_option(self):
"""Click on the 'Settings' option"""
self._hover_over_element(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_username"])
self._click(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_settings_option"])
# Sometimes the top-navbar is not hidden after clicking on the 'Settings' option. This
# action is to move the mouse to the top-left corner of the page to hide the top-navbar.
self._move_mouse_to_location(0, 0)
def click_on_inbox_option(self):
"""Click on the 'Inbox' option"""
self._hover_over_element(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_username"])
self._click(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_inbox_option"])
# Sometimes the top-navbar is not hidden after clicking on the 'Settings' option. This
# action is to move the mouse to the top-left corner of the page to hide the top-navbar.
self._move_mouse_to_location(0, 0)
def click_on_my_questions_profile_option(self):
"""Click on the 'My Questions' option"""
self._hover_over_element(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_username"])
self._click(self.TOP_NAVBAR_SIGNIN_SIGNUP_LOCATORS["signed_in_my_questions_option"])
# Sometimes the top-navbar is not hidden after clicking on the 'Settings' option. This
# action is to move the mouse to the top-left corner of the page to hide the top-navbar.
self._move_mouse_to_location(0, 0)
def get_text_of_logged_in_username(self) -> str:
"""Get the text of the logged in username"""

Просмотреть файл

@ -266,9 +266,10 @@ class MyProfileEdit(BasePage):
"""Click the cancel button"""
self._click(self.EDIT_PROFILE_PAGE_LOCATORS["cancel_button"])
def click_update_my_profile_button(self):
def click_update_my_profile_button(self, expected_url=None):
"""Click the update my profile button"""
self._click(self.EDIT_PROFILE_PAGE_LOCATORS["update_my_profile_button"], with_force=True)
self._click(self.EDIT_PROFILE_PAGE_LOCATORS["update_my_profile_button"],
expected_url=expected_url)
def click_close_account_option(self):
"""Click the close account and delete all profile information link"""
@ -277,8 +278,7 @@ class MyProfileEdit(BasePage):
def click_manage_firefox_account_button(self):
"""Click the manage firefox account button"""
self._click(self.EDIT_PROFILE_PAGE_LOCATORS["manage_firefox_account_button"],
with_wait=False)
self._click(self.EDIT_PROFILE_PAGE_LOCATORS["manage_firefox_account_button"])
def click_make_email_visible_checkbox(self, check: bool):
"""Click the make email visible checkbox"""

Просмотреть файл

@ -210,9 +210,13 @@ class MyProfilePage(BasePage):
"""Click on the given element."""
element.click()
def click_my_profile_page_sign_out_button(self):
"""Click on the profile page sign out button."""
self._click(self.PROFILE_DETAILS_LOCATORS["sign_out_button"])
def click_my_profile_page_sign_out_button(self, expected_url=None):
"""Click on the profile page sign out button.
Args:
expected_url (str): The expected URL after clicking the sign out button
"""
self._click(self.PROFILE_DETAILS_LOCATORS["sign_out_button"], expected_url=expected_url)
def click_on_report_abuse_option(self):
"""Click on the report abuse option."""
@ -222,9 +226,14 @@ class MyProfilePage(BasePage):
"""Click on the report abuse close button."""
self._click(self.REPORT_ABUSE_LOCATORS["report_abuse_close_panel_button"])
def click_on_private_message_button(self):
"""Click on the private message button."""
self._click(self.ADMIN_ACTIONS_LOCATORS["private_message_button"])
def click_on_private_message_button(self, expected_url=None):
"""Click on the private message button.
Args:
expected_url (str): The expected URL after clicking the private message button.
"""
self._click(self.ADMIN_ACTIONS_LOCATORS["private_message_button"],
expected_url=expected_url)
def publicly_displayed_email_element(self) -> Locator:
"""Get the locator for the publicly displayed email element."""

Просмотреть файл

@ -78,7 +78,7 @@
"article_discussions": "https://support.allizom.org/en-US/kb/all/discussions"
},
"groups": "https://support.allizom.org/en-US/groups/",
"testGroup1users": ["TEST_ACCOUNT_MESSAGE_1", "TEST_ACCOUNT_MESSAGE_2", "TEST_ACCOUNT_MESSAGE_3", "TEST_ACCOUNT_MESSAGE_4"],
"testGroup2users": ["TEST_ACCOUNT_MESSAGE_4", "TEST_ACCOUNT_MESSAGE_5", "TEST_ACCOUNT_MESSAGE_6"],
"testGroup1users": ["TEST_ACCOUNT_MESSAGE_1", "TEST_ACCOUNT_MESSAGE_2", "TEST_ACCOUNT_MESSAGE_3"],
"testGroup2users": ["TEST_ACCOUNT_MESSAGE_3", "TEST_ACCOUNT_MESSAGE_4"],
"test_article_link": "https://support.allizom.org/en-US/kb/donotdelete"
}

Различия файлов скрыты, потому что одна или несколько строк слишком длинны

Просмотреть файл

@ -349,7 +349,8 @@ def test_lock_and_archive_this_question(page: Page, status):
topic_name=sumo_pages.aaq_form_page.get_aaq_form_topic_options()[0],
body=utilities.aaq_question_test_data["valid_firefox_question"]
["simple_body_text"],
attach_image=False
attach_image=False,
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
with allure.step("Navigating to the first posted question"):
@ -519,7 +520,8 @@ def test_subscribe_to_feed_option(page: Page, is_firefox):
topic_name=sumo_pages.aaq_form_page.get_aaq_form_topic_options()[0],
body=utilities.aaq_question_test_data["valid_firefox_question"]
["simple_body_text"],
attach_image=False
attach_image=False,
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
with allure.step("Signing in with a different non admin user account and posting a "
@ -534,7 +536,8 @@ def test_subscribe_to_feed_option(page: Page, is_firefox):
topic_name=sumo_pages.aaq_form_page.get_aaq_form_topic_options()[0],
body=utilities.aaq_question_test_data["valid_firefox_question"]
["simple_body_text"],
attach_image=False
attach_image=False,
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
with allure.step("Navigating to the first question, clicking on the 'Subscribe to feed' "
@ -1944,7 +1947,8 @@ def post_firefox_product_question_flow(page: Page, username: str):
topic_name=sumo_pages.aaq_form_page.get_aaq_form_topic_options()[0],
body=utilities.aaq_question_test_data["valid_firefox_question"]
["simple_body_text"],
attach_image=False
attach_image=False,
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
return {"username_one": username_one, "question_details": question_details}

Просмотреть файл

@ -1,3 +1,5 @@
import warnings
import allure
import pytest
from playwright.sync_api import Page
@ -25,6 +27,7 @@ def navigate_to_homepage(page: Page):
502 error is encountered.
"""
if response.status == 502:
warnings.warn("502 encountered")
page = response.request.frame.page
print("502 error encountered. Reloading the page after 5 seconds.")
page.wait_for_timeout(5000)

Просмотреть файл

@ -366,7 +366,9 @@ def test_recent_revisions_dashboard_title_and_username_update(page: Page):
sumo_pages.top_navbar.click_on_edit_profile_option()
new_username = utilities.profile_edit_test_data['valid_user_edit']['username']
sumo_pages.edit_my_profile_page.send_text_to_username_field(new_username)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(new_username)
)
with allure.step("Navigating to the recent revisions dashboard and verifying that the "
"correct new username and article title arte displayed"):
@ -383,7 +385,9 @@ def test_recent_revisions_dashboard_title_and_username_update(page: Page):
with allure.step("Changing the username back"):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.send_text_to_username_field(first_username)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(first_username)
)
with allure.step("Deleting the article"):
utilities.navigate_to_link(article_url)

Просмотреть файл

@ -1,5 +1,4 @@
from typing import Any
import allure
from pytest_check import check
import pytest
@ -122,8 +121,10 @@ def test_kb_restrict_visibility(page: Page, create_delete_article, is_template):
utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_MODERATOR"]
))
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group(
utilities.kb_article_test_data['restricted_visibility_groups'][0])
utilities.re_call_function_on_error(
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group,
group_name=utilities.kb_article_test_data['restricted_visibility_groups'][0]
)
with allure.step("Signing in with an account belonging to the removed group"):
utilities.start_existing_session(utilities.username_extraction_from_email(
@ -151,7 +152,10 @@ def test_kb_restrict_visibility(page: Page, create_delete_article, is_template):
utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_MODERATOR"]
))
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group(group_name='')
utilities.re_call_function_on_error(
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group,
group_name=''
)
with allure.step("Deleting user session"):
utilities.delete_cookies()
@ -915,7 +919,10 @@ def remove_all_article_restrictions(page: Page):
utilities.user_secrets_accounts["TEST_ACCOUNT_MODERATOR"]
))
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group(group_name='')
utilities.re_call_function_on_error(
sumo_pages.edit_article_metadata_flow._remove_a_restricted_visibility_group,
group_name=''
)
def _create_discussion_thread(page: Page) -> dict[str, Any]:

Просмотреть файл

@ -80,7 +80,9 @@ def test_explore_by_topic_aaq_widget_text(page: Page):
.get_text_of_aaq_widget() == AAQWidgetMessages
.PREMIUM_AAQ_SUBHEADING_TEXT)
else:
assert not sumo_pages.explore_by_topic_page.is_aaq_text_visible()
assert (sumo_pages.explore_by_topic_page
.get_text_of_aaq_widget() == AAQWidgetMessages.
NEUTRAL_AAQ_SUBHEADING_TEXT)
# C2663960
@ -114,8 +116,7 @@ def test_explore_by_topic_aaq_widget_redirect(page: Page):
if product == "All Products":
assert ContactSupportMessages.PAGE_URL == utilities.get_page_url()
elif product not in utilities.aaq_question_test_data['products_aaq_url']:
assert (utilities.aaq_question_test_data['product_without_aaq_url'] == utilities.
get_page_url())
assert utilities.get_page_url() == ContactSupportMessages.PAGE_URL
else:
assert (utilities.
aaq_question_test_data['products_aaq_url'][product] == utilities.

Просмотреть файл

@ -30,7 +30,9 @@ def test_there_are_no_messages_here_text_is_displayed_when_no_messages_are_avail
if sumo_pages.inbox_page.are_inbox_messages_displayed():
with allure.step("Clearing the inbox since there are some existing messages"):
sumo_pages.inbox_page.delete_all_inbox_messages()
sumo_pages.inbox_page.delete_all_inbox_messages(
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
with check, allure.step("Verifying that the correct message is displayed"):
assert sumo_pages.inbox_page.get_text_of_inbox_no_message_header(
@ -41,7 +43,9 @@ def test_there_are_no_messages_here_text_is_displayed_when_no_messages_are_avail
if sumo_pages.sent_message_page.are_sent_messages_displayed():
with allure.step("Clearing sent messages list since there are some existing messages"):
sumo_pages.sent_message_page.delete_all_displayed_sent_messages()
sumo_pages.sent_message_page.delete_all_displayed_sent_messages(
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Verifying that the correct page message is displayed"):
assert sumo_pages.sent_message_page.get_sent_messages_no_message_text(
@ -70,7 +74,9 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
utilities.navigate_to_link(MyProfileMessages.get_my_profile_stage_url(username=user_two))
with allure.step("Clicking on the 'Private Message button'"):
sumo_pages.my_profile_page.click_on_private_message_button()
sumo_pages.my_profile_page.click_on_private_message_button(
expected_url=NewMessagePageMessages.NEW_MESSAGE_PAGE_STAGE_URL + f"?to={user_two}"
)
with allure.step("Verifying that the receiver is automatically added inside the 'To' "
"field"):
@ -83,7 +89,9 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
with allure.step("Sending a message to the user"):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
message_body=message_body)
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Verifying that the correct message sent banner is displayed"):
assert sumo_pages.inbox_page.get_text_inbox_page_message_banner_text(
@ -99,7 +107,9 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
with allure.step("Deleting the message from the sent messages page"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=message_body, from_sent_list=True)
excerpt=message_body, from_sent_list=True,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Verifying that the correct banner is displayed"):
assert sumo_pages.sent_message_page.get_sent_messages_page_deleted_banner_text(
@ -114,10 +124,6 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
utilities.user_secrets_accounts["TEST_ACCOUNT_MESSAGE_2"]
))
with allure.step("Verifying that the recipient user is visually notified about having a new "
"unread message"):
assert sumo_pages.top_navbar.is_unread_message_notification_displayed()
with allure.step("Accessing the Inbox section"):
sumo_pages.top_navbar.click_on_inbox_option()
@ -133,7 +139,9 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
with allure.step("Deleting the messages from the inbox section"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=message_body, from_inbox_list=True)
excerpt=message_body, from_inbox_list=True,
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
with allure.step("Verifying that the messages are no longer displayed inside the inbox"):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(excerpt=message_body)
@ -143,12 +151,6 @@ def test_private_messages_can_be_sent_via_user_profiles(page: Page, is_firefox):
assert sumo_pages.sent_message_page.get_sent_messages_page_deleted_banner_text(
) == SentMessagesPageMessages.DELETE_MESSAGE_BANNER_TEXT
with allure.step("Verifying that the notification and the unread messages counter is no "
"longer displayed near the user avatar"):
assert not sumo_pages.top_navbar.is_unread_message_notification_displayed()
sumo_pages.top_navbar.mouse_over_profile_avatar()
assert not sumo_pages.top_navbar.is_unread_message_notification_counter_visible()
# C891419
@pytest.mark.messagingSystem
@ -173,6 +175,7 @@ def test_private_message_can_be_sent_via_new_message_page(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=test_user,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Verifying that the correct banner is displayed"):
@ -187,7 +190,9 @@ def test_private_message_can_be_sent_via_new_message_page(page: Page):
with allure.step("Clearing the sent messages list"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=message_body, from_sent_list=True)
excerpt=message_body, from_sent_list=True,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Signing in with the receiver account and verifying that the message is "
"displayed inside the inbox section"):
@ -200,7 +205,9 @@ def test_private_message_can_be_sent_via_new_message_page(page: Page):
with allure.step("Clearing the inbox"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=message_body, from_inbox_list=True)
excerpt=message_body, from_inbox_list=True,
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
# C891412, C891413
@ -446,9 +453,9 @@ def test_messaging_system_unread_notification_after_message_deletion(page: Page)
utilities.user_secrets_accounts["TEST_ACCOUNT_13"]
)
with allure.step("Signing in with a non-admin user account"):
with allure.step("Signing in with an admin account"):
utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_12"]
utilities.user_secrets_accounts["TEST_ACCOUNT_MODERATOR"]
))
with allure.step("Accessing the inbox section and navigating to the new message page"):
@ -459,6 +466,7 @@ def test_messaging_system_unread_notification_after_message_deletion(page: Page)
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=test_user,
message_body=content_first_message,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
sumo_pages.mess_system_user_navbar.click_on_messaging_system_nav_new_message()
@ -466,10 +474,13 @@ def test_messaging_system_unread_notification_after_message_deletion(page: Page)
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=test_user,
message_body=content_second_message,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Deleting sent messages"):
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button()
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Signing in with the recipient"):
utilities.start_existing_session(utilities.username_extraction_from_email(
@ -504,7 +515,9 @@ def test_messaging_system_unread_notification_after_message_deletion(page: Page)
with allure.step("Deleting the first message"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=content_first_message, from_inbox_list=True)
excerpt=content_first_message, from_inbox_list=True,
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
with allure.step("Verifying that the new message notification counter resembles the unread "
"inbox message count"):
@ -532,7 +545,9 @@ def test_messaging_system_unread_notification_after_message_deletion(page: Page)
with allure.step("Deleting the second received message"):
sumo_pages.messaging_system_flow.delete_message_flow(
excerpt=content_second_message, from_inbox_list=True)
excerpt=content_second_message, from_inbox_list=True,
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
with allure.step("Verifying that the new message notification counter resembles the unread "
"inbox message count"):
@ -663,13 +678,18 @@ def test_messages_can_be_selected_and_deleted(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=test_user,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Navigating to the sent messages page"):
sumo_pages.mess_system_user_navbar.click_on_messaging_system_nav_sent_messages()
with allure.step("Clicking on the 'Delete Selected' button"):
sumo_pages.sent_message_page.click_on_delete_selected_button()
sumo_pages.sent_message_page.click_on_delete_selected_button(
expected_locator=(
sumo_pages.sent_message_page.SENT_MESSAGE_PAGE_LOCATORS
["sent_messages_page_message_banner_text"])
)
with check, allure.step("Verifying that the correct message is displayed"):
assert sumo_pages.sent_message_page.get_sent_messages_page_deleted_banner_text(
@ -687,19 +707,24 @@ def test_messages_can_be_selected_and_deleted(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=username_one,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Clicking on the 'delete selected' button while no messages is "
"selected and verifying that the correct banner is displayed"):
sumo_pages.mess_system_user_navbar.click_on_messaging_system_navbar_inbox()
sumo_pages.inbox_page.click_on_inbox_delete_selected_button()
sumo_pages.inbox_page.click_on_inbox_delete_selected_button(
expected_locator=sumo_pages.inbox_page.INBOX_PAGE_LOCATORS
['inbox_page_message_action_banner']
)
assert sumo_pages.inbox_page.get_text_inbox_page_message_banner_text(
) in InboxPageMessages.NO_MESSAGES_SELECTED_BANNER_TEXT
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body).first
).to_be_visible()
with allure.step("Selecting the messages and deleting it via the delete selected button"):
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(message_body)
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
with check, allure.step("Verifying that the messages are no longer displayed"):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body)).to_be_hidden()
@ -710,7 +735,7 @@ def test_messages_can_be_selected_and_deleted(page: Page):
"the 'delete selected button'"):
sumo_pages.mess_system_user_navbar.click_on_messaging_system_nav_sent_messages()
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
message_body)
message_body, expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL)
with allure.step("Verifying that the messages are no longer displayed"):
expect(sumo_pages.sent_message_page.sent_messages_by_excerpt_locator(message_body)
@ -731,7 +756,8 @@ def test_messages_can_be_selected_and_deleted(page: Page):
with allure.step("Deleting all messages from the inbox page via the delete selected "
"button'"):
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(message_body)
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
with check, allure.step("Verifying that the messages are no longer displayed inside the "
"inbox section and the correct banner is displayed"):
@ -804,6 +830,7 @@ def test_staff_users_can_send_group_messages(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=targeted_test_group,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Navigating to the 'Sent Messages page' and verifying that the message "
@ -815,7 +842,7 @@ def test_staff_users_can_send_group_messages(page: Page):
with allure.step("Deleting the outbox"):
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
message_body)
message_body, expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL)
with allure.step("Signing in with all targeted group members, verifying that the message "
"was received and clearing the inbox"):
@ -828,7 +855,7 @@ def test_staff_users_can_send_group_messages(page: Page):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body)
).to_be_visible()
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body)
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
with allure.step("Signing in with users from second test group and verifying that the "
"message was not received"):
@ -862,6 +889,7 @@ def test_staff_users_can_send_messages_to_multiple_groups(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=targeted_test_group,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Navigating to the 'Sent Messages page' and verifying that the "
@ -874,7 +902,7 @@ def test_staff_users_can_send_messages_to_multiple_groups(page: Page):
with allure.step("Deleting the outbox"):
utilities.navigate_back()
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
message_body)
message_body, expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL)
with allure.step("Signing in with all targeted group members, verifying that the message "
"was received and clearing the inbox"):
@ -888,7 +916,7 @@ def test_staff_users_can_send_messages_to_multiple_groups(page: Page):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body)
).to_be_visible()
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body)
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
# C2566118, C2566119, C2566120
@ -905,7 +933,7 @@ def test_staff_users_can_send_messages_to_both_groups_and_user(page: Page):
targeted_user = [utilities.username_extraction_from_email(
utilities.user_secrets_accounts['TEST_ACCOUNT_MESSAGE_4']),
utilities.username_extraction_from_email(
utilities.user_secrets_accounts['TEST_ACCOUNT_12'])]
utilities.user_secrets_accounts['TEST_ACCOUNT_MESSAGE_5'])]
with allure.step("Navigating to the new messages page"):
sumo_pages.top_navbar.click_on_inbox_option()
@ -915,6 +943,7 @@ def test_staff_users_can_send_messages_to_both_groups_and_user(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=targeted_user + [targeted_test_group],
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with check, allure.step("Navigating to the 'Sent Messages page' and verifying that the "
@ -923,16 +952,17 @@ def test_staff_users_can_send_messages_to_both_groups_and_user(page: Page):
sumo_pages.sent_message_page.click_on_sent_message_subject(message_body)
check.is_in(targeted_test_group,
sumo_pages.sent_message_page.get_text_of_all_sent_groups())
check.equal(targeted_user, sumo_pages.sent_message_page.get_text_of_all_recipients())
check.equal(set(targeted_user),
set(sumo_pages.sent_message_page.get_text_of_all_recipients()))
with allure.step("Deleting the outbox"):
utilities.navigate_back()
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
message_body)
message_body, expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL)
with allure.step("Signing in with all targeted group members, verifying that the message "
"was received and clearing the inbox"):
for user in utilities.general_test_data['testGroup1users'] + ['TEST_ACCOUNT_12']:
for user in utilities.general_test_data['testGroup1users'] + ['TEST_ACCOUNT_MESSAGE_5']:
utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts[user]
))
@ -941,7 +971,7 @@ def test_staff_users_can_send_messages_to_both_groups_and_user(page: Page):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body)
).to_be_visible()
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body)
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
# C2566116
@ -973,11 +1003,12 @@ def test_removed_group_users_do_not_receive_group_messages(page: Page):
sumo_pages.messaging_system_flow.complete_send_message_form_with_data(
recipient_username=targeted_test_group,
message_body=message_body,
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)
with allure.step("Deleting the outbox"):
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
message_body)
message_body, expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL)
with allure.step("Signing in with all targeted group members, verifying that the message "
"was received and clearing the inbox"):
@ -997,7 +1028,7 @@ def test_removed_group_users_do_not_receive_group_messages(page: Page):
expect(sumo_pages.inbox_page._inbox_message_based_on_excerpt(message_body)
).to_be_visible()
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
message_body)
message_body, expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL)
with allure.step("Signing in with an staff account and adding the user back to the group"):
utilities.start_existing_session(utilities.username_extraction_from_email(
@ -1038,7 +1069,7 @@ def test_clear_inbox_and_outbox(page: Page):
utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts[user]
))
sumo_pages.top_navbar.click_on_inbox_option()
utilities.navigate_to_link(InboxPageMessages.INBOX_PAGE_STAGE_URL)
inbox_and_outbox_deletion(page)
utilities.delete_cookies()
@ -1052,8 +1083,12 @@ def test_clear_inbox_and_outbox(page: Page):
def inbox_and_outbox_deletion(page: Page):
sumo_pages = SumoPages(page)
if sumo_pages.inbox_page.are_inbox_messages_displayed():
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button()
sumo_pages.inbox_page.delete_all_inbox_messages_via_delete_selected_button(
expected_url=InboxPageMessages.INBOX_PAGE_STAGE_URL
)
sumo_pages.mess_system_user_navbar.click_on_messaging_system_nav_sent_messages()
if sumo_pages.sent_message_page.are_sent_messages_displayed():
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button()
sumo_pages.sent_message_page.delete_all_sent_messages_via_delete_selected_button(
expected_url=SentMessagesPageMessages.SENT_MESSAGES_PAGE_URL
)

Просмотреть файл

@ -62,7 +62,9 @@ def test_edit_profile_field_validation_with_symbols(page: Page, is_firefox):
sumo_pages.edit_my_profile_page.send_text_to_username_field(new_username)
with allure.step("Clicking on the 'Update My Profile' button"):
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(new_username)
)
with check, allure.step("Verify that the newly set username is successfully applied to the my "
"profile section"):
@ -84,7 +86,9 @@ def test_edit_profile_field_validation_with_symbols(page: Page, is_firefox):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.clear_username_field()
sumo_pages.edit_my_profile_page.send_text_to_username_field(original_username)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(original_username)
)
with check, allure.step("Verifying that the username was updated back to the original one"):
assert sumo_pages.my_profile_page.get_my_profile_display_name_header_text(
@ -277,7 +281,9 @@ def test_username_can_contain_uppercase_and_lowercase_letters(page: Page):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.clear_username_field()
sumo_pages.edit_my_profile_page.send_text_to_username_field(new_username)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(new_username)
)
with allure.step("Verifying that the username displayed inside the top-navbar updates "
"successfully"):
@ -292,7 +298,9 @@ def test_username_can_contain_uppercase_and_lowercase_letters(page: Page):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.clear_username_field()
sumo_pages.edit_my_profile_page.send_text_to_username_field(original_username)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(original_username)
)
# C1491463, C1491464
@ -301,7 +309,7 @@ def test_display_name_replaces_the_username_text(page: Page, is_firefox):
utilities = Utilities(page)
sumo_pages = SumoPages(page)
with allure.step("Signing in with a non-admin account"):
utilities.start_existing_session(utilities.username_extraction_from_email(
username = utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts['TEST_ACCOUNT_MESSAGE_1']
))
@ -320,7 +328,9 @@ def test_display_name_replaces_the_username_text(page: Page, is_firefox):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.clear_display_name_field()
sumo_pages.edit_my_profile_page.send_text_to_display_name_field(new_display_name)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(username)
)
with allure.step("Verifying that the top navbar username updates with the display name"):
assert sumo_pages.top_navbar.get_text_of_logged_in_username() == new_display_name
@ -333,7 +343,9 @@ def test_display_name_replaces_the_username_text(page: Page, is_firefox):
with allure.step("Reverting back and deleting the display name"):
sumo_pages.top_navbar.click_on_edit_profile_option()
sumo_pages.edit_my_profile_page.clear_display_name_field()
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(username)
)
with allure.step(f"Verifying that the displayed name inside the top navbar is reverted "
f"back to {original_username}"):
@ -352,7 +364,7 @@ def test_biography_field_accepts_html_tags(page: Page):
utilities = Utilities(page)
sumo_pages = SumoPages(page)
with allure.step("Signing in with a non-admin user account"):
utilities.start_existing_session(utilities.username_extraction_from_email(
username = utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_12"]
))
@ -364,7 +376,9 @@ def test_biography_field_accepts_html_tags(page: Page):
sumo_pages.edit_my_profile_page.send_text_to_biography_field(
html_test_data["biography_field_with_html_data"]["biography_html_data"]
)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(username)
)
# T5697917
@ -375,7 +389,7 @@ def test_make_my_email_address_visible_checkbox_checked(page: Page):
logged_in_email = utilities.user_secrets_accounts["TEST_ACCOUNT_12"]
with allure.step("Signing in with a non-admin account"):
utilities.start_existing_session(utilities.username_extraction_from_email(
username = utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_12"]
))
username_one = sumo_pages.top_navbar.get_text_of_logged_in_username()
@ -385,7 +399,9 @@ def test_make_my_email_address_visible_checkbox_checked(page: Page):
sumo_pages.top_navbar.click_on_edit_profile_option()
if not sumo_pages.edit_my_profile_page.is_make_email_visible_checkbox_selected():
sumo_pages.edit_my_profile_page.click_make_email_visible_checkbox(check=True)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(username)
)
else:
sumo_pages.top_navbar.click_on_view_profile_option()
@ -420,7 +436,7 @@ def test_make_my_email_address_visible_checkbox_unchecked(page: Page):
utilities = Utilities(page)
sumo_pages = SumoPages(page)
with allure.step("Signing in with a non-admin user account"):
utilities.start_existing_session(utilities.username_extraction_from_email(
username = utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_MESSAGE_1"]
))
username_one = sumo_pages.top_navbar.get_text_of_logged_in_username()
@ -430,7 +446,9 @@ def test_make_my_email_address_visible_checkbox_unchecked(page: Page):
sumo_pages.top_navbar.click_on_edit_profile_option()
if sumo_pages.edit_my_profile_page.is_make_email_visible_checkbox_selected():
sumo_pages.edit_my_profile_page.click_make_email_visible_checkbox(check=False)
sumo_pages.edit_my_profile_page.click_update_my_profile_button()
sumo_pages.edit_my_profile_page.click_update_my_profile_button(
expected_url=MyProfileMessages.get_my_profile_stage_url(username)
)
with allure.step("Verifying that the email is not displayed"):
expect(sumo_pages.my_profile_page.publicly_displayed_email_element()).to_be_hidden()
@ -453,13 +471,14 @@ def test_profile_information(page: Page):
utilities = Utilities(page)
sumo_pages = SumoPages(page)
with allure.step("Signing in with a non-admin user"):
utilities.start_existing_session(utilities.username_extraction_from_email(
username = utilities.start_existing_session(utilities.username_extraction_from_email(
utilities.user_secrets_accounts["TEST_ACCOUNT_12"]
))
username_one = sumo_pages.top_navbar.get_text_of_logged_in_username()
sumo_pages.top_navbar.click_on_edit_profile_option()
profile_info = sumo_pages.edit_profile_flow.edit_profile_with_test_data(
info_only=True, submit_change=True)
info_only=True, submit_change=True,
expected_url=MyProfileMessages.get_my_profile_stage_url(username))
profile_info_keys = [
"website", "twitter", "community_portal", "people_directory", "matrix_nickname",
@ -592,7 +611,9 @@ def test_private_message_button_redirects_non_signed_in_users_to_the_fxa_login_f
with allure.step("Clicking on the 'Private Message' button and verifying that the non-signed "
"in user is redirected to the fxa page"):
sumo_pages.my_profile_page.click_on_private_message_button()
sumo_pages.my_profile_page.click_on_private_message_button(
expected_url=FxAPageMessages.AUTH_PAGE_URL
)
assert (
sumo_pages.auth_page.is_continue_with_firefox_button_displayed()
), "The auth page is not displayed! It should be!"
@ -667,8 +688,6 @@ def _validate_profile_info(page: Page, target: str, profile_info: str, username:
"involved_from_year": sumo_pages.my_profile_page.get_my_contributed_from_text,
}
link_click_methods = {
"website": sumo_pages.my_profile_page.click_on_my_website_link,
"twitter": sumo_pages.my_profile_page.click_on_twitter_link,
"community_portal": sumo_pages.my_profile_page.click_on_community_portal_link,
"people_directory": sumo_pages.my_profile_page.click_on_people_directory_link,
}

Просмотреть файл

@ -54,7 +54,9 @@ def test_my_profile_sign_out_button_functionality(page: Page):
with allure.step("Accessing the my profile page, clicking on the sign out button and "
"verifying that the user is redirected to the homepage"):
sumo_pages.top_navbar.click_on_view_profile_option()
sumo_pages.my_profile_page.click_my_profile_page_sign_out_button()
sumo_pages.my_profile_page.click_my_profile_page_sign_out_button(
expected_url=HomepageMessages.STAGE_HOMEPAGE_URL_EN_US
)
expect(page).to_have_url(HomepageMessages.STAGE_HOMEPAGE_URL_EN_US)
with allure.step("Verify that the 'Sign in/Up' button from the page header is displayed"):
@ -81,7 +83,8 @@ def test_provided_solutions_number_is_successfully_displayed(page: Page):
topic_name=utilities.
aaq_question_test_data["valid_firefox_question"]["topic_value"],
body=utilities.
aaq_question_test_data["valid_firefox_question"]["question_body"]
aaq_question_test_data["valid_firefox_question"]["question_body"],
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
)
@ -158,7 +161,8 @@ def test_number_of_my_profile_answers_is_successfully_displayed(page: Page):
topic_name=utilities.
aaq_question_test_data["valid_firefox_question"]["topic_value"],
body=utilities.
aaq_question_test_data["valid_firefox_question"]["question_body"]
aaq_question_test_data["valid_firefox_question"]["question_body"],
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
)

Просмотреть файл

@ -37,7 +37,8 @@ def test_number_of_questions_is_incremented_when_posting_a_question(page: Page):
topic_name=utilities
.aaq_question_test_data["valid_firefox_question"]["topic_value"],
body=utilities.
aaq_question_test_data["valid_firefox_question"]["question_body"]
aaq_question_test_data["valid_firefox_question"]["question_body"],
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
)
with allure.step("Navigating back to the profile page and verifying that the number of "
@ -116,7 +117,9 @@ def test_correct_messages_is_displayed_if_user_has_no_posted_questions(page: Pag
topic_name=utilities
.aaq_question_test_data["valid_firefox_question"]["topic_value"],
body=utilities.
aaq_question_test_data["valid_firefox_question"]["question_body"]
aaq_question_test_data["valid_firefox_question"]["question_body"],
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
)
@ -178,7 +181,8 @@ def test_my_question_page_reflects_posted_questions_and_redirects_to_the_correct
topic_name=utilities.
aaq_question_test_data["valid_firefox_question"]["topic_value"],
body=utilities.
aaq_question_test_data["valid_firefox_question"]["question_body"]
aaq_question_test_data["valid_firefox_question"]["question_body"],
expected_locator=sumo_pages.question_page.QUESTION_LOCATORS["questions_header"]
)
)