class HmsAppConfigTests(unittest.TestCase): """ Positive and negative tests for the HMS App Config page. """ log = custom_logger(logging.DEBUG) @classmethod def setUpClass(cls): driver_object = DriverFactory() cls.driver = driver_object.get_web_driver("firefox") login_page = PageFactory.get_page_object("login", cls.driver) login_page.login() time.sleep(3) def test_happy_path_visit_hms_app_config_page(self): """ Visiting the HMS App Config page; then verifying all table column texts """ hms_app_config_page = PageFactory.get_page_object( "hmsappconfig", self.driver) hms_app_config_page.verify_table_first_column() hms_app_config_page.verify_table_second_column() @classmethod def tearDownClass(cls): pass
class FindMemberPageTests(unittest.TestCase): """ Positive and negative tests for the HMS Find Member page. """ log = custom_logger(logging.DEBUG) @classmethod def setUpClass(cls): driver_object = DriverFactory() cls.driver = driver_object.get_web_driver("firefox") login_page = PageFactory.get_page_object("login", cls.driver) login_page.login() time.sleep(3) def test_happy_path_visit_find_member_page(self): """ Visiting the HMS Find Member page; then entering a valid member ID and clicking on Fetch button. """ find_member_page = PageFactory.get_page_object("findmember", self.driver) find_member_page.fetch_member() time.sleep(3) member_detail_page = PageFactory.get_page_object_with_id_memberid( "memberdetail", self.driver, config.LOCAL_TDOBER['FETCH_ID'].strip("\n"), config.LOCAL_TDOBER['FETCH_MEMBERID'].strip("\n")) print(member_detail_page.verify_points()) @classmethod def tearDownClass(cls): pass
class FindMemberPage(BasePage): """ Page Object Model for the HMS Find Member page. Methods: start: to visit the page this class is modeling, using the inherited (fom BasePage) open method """ log = custom_logger(logging.DEBUG) def start(self): """ The start method also verifies the page title after getting the url. """ self.url = '/member/find' self.open(self.url) self.log.info("Starting the find member page ") self.assertIn("HMS: Find Member", self._driver.title) def fetch_member(self): self.enter_member_id(config.LOCAL_TDOBER['FETCH_MEMBERID'].strip("\n")) self.click_fetch_button() def enter_member_id(self, member_id): self.sendKeys(member_id, FindMemberPageLocators.MEMBER_ID_FIELD, "id") def click_fetch_button(self): self.elementClick(FindMemberPageLocators.FETCH_BUTTON, "xpath")
class HmsAppConfigPage(BasePage): """ Page Object Model for the HMS Admin AppConfig page. Methods: start: to visit the page this class is modeling, using the inherited (fom BasePage) open method """ log = custom_logger(logging.DEBUG) def start(self): """ The start method also verifies the page title after getting the url. """ self.url = '/hmsappconfig/list' self.open(self.url) self.log.info("Starting the HMS App Config page ") self.assertIn("HMS: HMSAppConfig", self._driver.title) def verify_table_first_column(self): self.isElementPresent(HmsAppConfigPageLocators.TABLE_FIRST_COLUMN_USER_ID, "xpath") element = self.getElement(HmsAppConfigPageLocators.TABLE_FIRST_COLUMN_USER_ID, "xpath") self.assertEqual(config.LOCAL_TDOBER['TABLE_FIRST_COLUMN_TEXT'].strip("\n"), element.text) return element.text def verify_table_second_column(self): self.isElementPresent(HmsAppConfigPageLocators.TABLE_SECOND_COLUMN_USER_ID, "xpath") element = self.getElement(HmsAppConfigPageLocators.TABLE_SECOND_COLUMN_USER_ID, "xpath") self.assertEqual(config.LOCAL_TDOBER['TABLE_SECOND_COLUMN_TEXT'].strip("\n"), element.text) return element.text
class LoginPage(BasePage): """ Page Object Model for the HMS Admin login page. Methods: start: to visit the page this class is modeling, using the inherited (fom BasePage) open method login: to perform the actual login. Returns True or False enter_username enterPassword clickLoginButton verify_that_logged_in: using xpath locators ut verifies that we are actually on the expected page """ log = custom_logger(logging.DEBUG) def start(self): """ The start method also verifies the page title after getting the url. """ self.url = '/config/list' self.open(self.url) self.log.info("Starting the login page ") self.assertIn("HMS", self._driver.title) def login(self): file_reader = FileReader() username = file_reader.get_username() self.enter_username(username.strip("\n")) file_reader = FileReader() password = file_reader.get_password() self.enterPassword(password.strip("\n")) self.clickLoginButton() if 'HMS' in self._driver.title: self.log.debug("Successful login ") return True else: self.log.debug("Login failed ") return False def enter_username(self, username): self.sendKeys(username, LoginPageLocators.USERNAME_FIELD, "name") def enterPassword(self, password): self.sendKeys(password, LoginPageLocators.PASSWORD_FIELD, "name") def clickLoginButton(self): self.elementClick(LoginPageLocators.LOGIN_BUTTON, "name") def verify_that_logged_in(self): self.assertTrue(self.isElementPresent(MainPageLocators.ACTIVE_CLASS, "xpath"), "We are not on the expected page") self.assertTrue(self.isElementPresent(MainPageLocators.ACTIVE_CLASS_CONTAINS, "xpath"), "We are not on the expected page")
class LocalRecTeamMemberAdminPage(BasePage): log = custom_logger(logging.DEBUG) def start(self): """ The start method also verifies the page title after getting the url. """ self.url = '/localRecTeamMember/userList' self.open(self.url) self.log.info("Starting the LocalRec TeamMember Admin page ") self.assertIn("Local Recommendations Team Member Admin", self._driver.title) def verify_table_first_column(self): self.isElementPresent(LocalRecTeamMemberAdminPageLocators.TABLE_FIRST_COLUMN_USER_ID, "xpath") element = self.getElement(LocalRecTeamMemberAdminPageLocators.TABLE_FIRST_COLUMN_USER_ID, "xpath") self.assertEqual(config.LOCAL_TDOBER['TEAM_MEMBER_ADMIN_FIRST_COLUMN_TEXT'].strip("\n"), element.text) return element.text
class LoginTests(unittest.TestCase): log = custom_logger(logging.DEBUG) """ Positive and negative tests for the login feature. """ @classmethod def setUpClass(cls): driver_object = DriverFactory() cls.driver = driver_object.get_web_driver("ff") # driver.maximize_window() def test_happy_path_login(self): """ Positive test for the login feature. Providing valid username and password enables user to log in. """ login_page_object = PageFactory.get_page_object("login", self.driver) self.assertTrue(login_page_object.login(), "Login failed") time.sleep(3) login_page_object.verify_that_logged_in() @classmethod def tearDownClass(cls): cls.driver.quit()
class MemberDetailPage(BasePage): """ Page Object Model for the HMS Member Detail page. Methods: start: to visit the page this class is modeling, using the inherited (fom BasePage) open method verify_points: reads the Points value from the Member Detail page and compares it to the value from the config file. """ log = custom_logger(logging.DEBUG) def __init__(self, selenium_driver, id, memberid, base_url): # super().__init__(selenium_driver, base_url=config.LOCAL_TDOBER['BASE_URL']) self._base_url = base_url = config.LOCAL_TDOBER['BASE_URL'] self._driver = selenium_driver self._id = id self._memberid = memberid if self._driver is not None: self.start(id, memberid) def start(self, id, memberid): """ The start method also verifies the page title after getting the url. """ self.url = "member/detail?id={}&memberid={}".format(id, memberid) self.open(self.url) self.log.info("Starting the find member page ") self.assertIn("HMS: Member Info", self._driver.title) def verify_points(self): self.assertTrue( self.isElementPresent(MemberDetailPageLocators.POINTS, "xpath"), "We are not on the expected page") element = self.getElement(MemberDetailPageLocators.POINTS, "xpath") print(element.text) print(config.LOCAL_TDOBER['FETCHED_MEMBER_POINTS']) # self.assertEqual(config.LOCAL_TDOBER['FETCHED_MEMBER_POINTS'], element.text) return element.text
class LocalRecTeamMemberAdminTests(unittest.TestCase): log = custom_logger(logging.DEBUG) """ Verifying LocalRec team admin page; the table elements and then the import and delete functions on the page. """ @classmethod def setUpClass(cls): driver_object = DriverFactory() cls.driver = driver_object.get_web_driver("firefox") login_page = PageFactory.get_page_object("login", cls.driver) login_page.login() time.sleep(3) def test_happy_path_visit_teamMember_admin_page(self): """ Visiting the page then verifying all table column texts """ team_member_admin_page = PageFactory.get_page_object( "teammemberadmin", self.driver) team_member_admin_page.verify_table_first_column() @classmethod def tearDownClass(cls): pass
class BasePage(unittest.TestCase): """ This class is serving basic attributes/functions for every single page inherited from it. Attributes: selenium_driver: allows you to drive the browser. base_url: The HMS Admin Console base URL unless passed in differently Methods: start: Page Object Model classes, extending BasePage, need to specify their own relative URL open: invokes the driver's get method to visit the page in question """ log = custom_logger(logging.DEBUG) def __init__(self, selenium_driver, base_url=config.LOCAL_TDOBER['BASE_URL']): super().__init__() self._base_url = base_url self._driver = selenium_driver if self._driver is not None: self.start() def start(self): """ Overwrite this method in your Page module to visit the given page's URL. Provide a relative URL there like '/config/list' """ pass def open(self, url): """ Provide a relative URL for this method in your Page module """ url = self._base_url + url self._driver.get(url) """ Webdriver-related methods to be used in Page modules """ def getElement(self, locator, strategy): """ Receives the locator type (with other words, strategy) like By.NAME and uses the webdriver's find_element method. Returns the found WebElement. See doc at https://seleniumhq.github.io/selenium/docs/api/py/webdriver_remote/selenium.webdriver.remote.webdriver.html?highlight=find_element#selenium.webdriver.remote.webdriver.WebDriver.find_element """ element = None try: strategy = strategy.lower() by_type = self.getByType(strategy) element = self._driver.find_element(by_type, locator) self.log.debug("Element Found with locator: {} and strategy: {}".format(locator, strategy)) except NoSuchElementException: self.log.debug("Element not found with locator: " + locator + " and strategy: " + strategy) return element def getByType(self, locator_type): """ Helper method to find the appropriate Selenium locator strategy like By.NAME. See doc at https://seleniumhq.github.io/selenium/docs/api/py/webdriver/selenium.webdriver.common.by.html?highlight=by#selenium.webdriver.common.by :param locator_type: :return: selenium.webdriver.common.by """ locator_type = locator_type.lower() if locator_type == "id": return By.ID elif locator_type == "name": return By.NAME elif locator_type == "xpath": return By.XPATH elif locator_type == "css": return By.CSS_SELECTOR elif locator_type == "class": return By.CLASS_NAME elif locator_type == "link": return By.LINK_TEXT elif locator_type == "tag": return By.TAG_NAME elif locator_type == "link text": return By.LINK_TEXT elif locator_type == "partial link text": return By.PARTIAL_LINK_TEXT else: self.log.debug("Locator type {} not correct/supported".format(locator_type)) return False def sendKeys(self, data, locator, locator_type="name"): """ After locating the WebElement we want to send some data, like entering username :param data: the actual data :param locator: from the LoginPageLocators class, where they are grouped by page :param locator_type: name or xpath or id etc. """ try: element = self.getElement(locator, locator_type) element.send_keys(data) self.log.debug( "Sent data {} with locator: {} and locatorType: {} ".format(data, locator, locator_type)) except ElementNotVisibleException: self.log.debug("Cannot send data on the element with locator: " + locator + " locatorType: " + locator_type) print_stack() def elementClick(self, locator, locator_type="name"): """ After locating a button we want to click on it :param locator: from the LoginPageLocators class, where they are grouped by page :param locator_type: name or xpath or id etc. """ try: element = self.getElement(locator, locator_type) element.click() self.log.debug("Clicked on element with locator: {} and locator_type: {} ".format(locator, locator_type)) except ElementNotVisibleException: self.log.debug( "Cannot click on the element with locator: {} and locator_type: {}".format(locator, locator_type)) print_stack() def isElementPresent(self, locator, locator_type="id"): """ Verifying that webdriver can locate the element on the page :param locator: from the LoginPageLocators class, where they are grouped by page :param locator_type: name or xpath or id etc. :return: True or False """ try: element = self.getElement(locator, locator_type) if element is not None: self.log.debug("Element {} was found".format(element.text)) return True else: self.log.debug("Element for locator {} was not found".format(locator)) return False except NoSuchElementException: self.log.debug("Element was not found") return False def waitForElement(self, locator, locator_type="id", timeout=10, poll_frequency=0.5): """ Method to perform intelligent waits. It tries to find the element with a specified frequency. :param locator: from the LoginPageLocators class, where they are grouped by page :param locator_type: name or xpath or id etc. :param timeout: in seconds :param poll_frequency: in seconds :return: element """ element = None try: by_type = self.getByType(locator_type) self.log.debug("Waiting for maximum :: " + str(timeout) + " :: seconds for element to be clickable") wait = WebDriverWait(self._driver, timeout, poll_frequency=poll_frequency, ignored_exceptions=[NoSuchElementException, ElementNotVisibleException, ElementNotSelectableException]) element = wait.until(expected_conditions.element_to_be_clickable((by_type, locator))) self.log.debug("Element appeared on the web page") except NoSuchElementException: self.log.debug("Element not appeared on the web page") print_stack() return element