During the UI automation testing process, faced with complex business scenarios, we often encounter the following challenges:
- Simple recording/playback is fast, but cannot adapt to complex scenes;
- Writing automated test scripts is more flexible, but the workload is heavy and maintainability is poor;
- The previous encapsulation technology (PageObject) can adapt to various UI scenarios, but its structure is loose and cannot be migrated across multiple projects;
Therefore, testing teams often also need a custom testing framework to compensate for the shortcomings of the existing framework.
Test framework encapsulation idea
Since the UI automated testing framework is used around the UI interface, the PageObject design pattern is still used to encapsulate the UI and tests. At the same time, it cooperates with the Pytest unit test to effectively organize and apply the scripts coherently, thereby improving the maintainability and readability of the framework. sex.
Since the test framework is based on the PageObject design pattern, the main directions are PO improvement, data-driven, exception handling, etc., such as:
- Data-driven test data: store data in external yaml files and use yaml tools to read data;
- Data-driven data steps: Put the operation steps into an external yaml file, use the yaml tool to read the operation steps, and use special functions to parse and implement the operation steps;
- Automated exception handling mechanism: Encapsulate and improve the element search module, including how to handle pop-up windows;
Page_Object Transformation
As a general UI testing framework, PageObjet is not only suitable for web automated testing, but also Appium mobile automated testing. Its advantages are as follows:
- Reduce code duplication
- Improve test case readability
- Improve test case maintainability
PO transformation example (based on Snowball App)
This case will encapsulate and improve Snowball App with Page Object.
When you start the Snowball App, you will enter the homepage. Click the search box to enter the search page, search for a stock and determine whether the stock price is greater than 200:
The module relationship of PageObject is as follows. All modules must inherit BasePage. App implements operations such as starting, restarting, and stopping. Main implements operations such as entering the search page and entering the stock page:
Now I have also found a lot of test friends and created a communication group to share technology, sharing a lot of technical documents and video tutorials we collected. If you don’t want to experience the feeling of not being able to find resources when studying on your own, having no one to answer your questions, and persisting for a few days before giving up. You can join us to communicate. And there are many technical experts who have made certain achievements in automation, performance, security, test development, etc. Share their experience, and also share many live lectures and technical salons You can learn for free! Focus on it! Open source! ! ! QQ group number: 110685036 [password: csdn999]
The base_page module is the parent class of all page classes, which defines public methods. For example, after encapsulating the find method below, subclasses can call find:
from appium.webdriver.webdriver import WebDriver classBasePage: _driver: WebDriver def __init__(self, driver: WebDriver = None): self._driver = driver def find(self, locator, value: str = None): #If a tuple is passed in, just use one parameter: locator if isinstance(locator, tuple): return self._driver.find_element(*locator) else: return self._driver.find_element(locator, value)
The App module encapsulates the app’s startup, restart, stop and other methods. When the app starts, it will enter the main page, so the main method below must return Main. The definition of the Main class will be explained later:
from appium import webdriver from test_appium.page.base_page import BasePage from test_appium.page.main import Main class App(BasePage): #Specify the package name and activity name of the app _package = "com.xueqiu.android" _activity = ".view.WelcomeActivityAlias" def start(self): #Initialize if driver is empty if self._driver is None: caps = {} caps["platformName"] = "android" caps["deviceName"] = "hogwarts" caps["appPackage"] = self._package caps["appActivity"] = self._activity caps["noReset"] = True #Initialize driver self._driver = webdriver.Remote("http://localhost:4723/wd/hub", caps) self._driver.implicitly_wait(30) #If the driver is not empty, start the activity directly else: print(self._driver) self._driver.start_activity(self._package, self._activity) return self def restart(self): pass def stop(self): pass def main(self) -> Main: #When the app starts, jump to (instantiate) Main return Main(self._driver)
The Main module is the PageObject of the homepage, and its methods encapsulate important functions of the homepage. For example, goto_search_page in the following code encapsulates click search and jumps to the Search page:
from appium.webdriver.common.mobileby import MobileBy from selenium.webdriver.common.by import By from test_appium.page.base_page import BasePage from test_appium.page.profile import Profile from test_appium.page.search import Search class Main(BasePage): #After clicking the search button, enter the search page def goto_search_page(self): self.find(MobileBy.ID, "tv_search").click() #Enter the search page return Search(self._driver) def goto_stocks(self): pass def goto_trade(self): pass def goto_messages(self): pass
The Search module can search for a stock and obtain the price of the stock, such as the following figure:
The packaging code is as follows:
from appium.webdriver.common.mobileby import MobileBy from selenium.webdriver.remote.webdriver import WebDriver class Search: _driver: WebDriver def __init__(self, driver): self._driver = driver #Enter what you want to search for def search(self, key: str): self._driver.find_element(MobileBy.ID, "search_input_text").send_keys(key) self._driver.find_element(MobileBy.ID, "name").click() return self #Get the stock price for judgment def get_price(self, key: str) -> float: return float(self._driver.find_element(MobileBy.ID, "current_price").text)
Finally, create a test for the above code and create a new test module test_search:
import pytest from test_appium.page.app import App class TestSearch: def setup(self): self.main = App().start().main() def test_search(self): assert self.main.goto_search_page().search("alibaba").get_price("BABA") > 200
The above is for your reference, please leave a message to discuss together.
Finally, I would like to thank everyone who has read my article carefully. Looking at the increase in fans and attention, there is always some courtesy. Although it is not a very valuable thing, if you can use it, you can take it directly!
Software testing interview documents
We must study to find a high-paying job. The following interview questions are from the latest interview materials from first-tier Internet companies such as Alibaba, Tencent, Byte, etc., and some Byte bosses have given authoritative answers. After finishing this set I believe everyone can find a satisfactory job based on the interview information.