一.POM设计模式
pom指的是page object module,po模式,也就是说会把每个页面当做一个对象来对待,而该页面下的动作都会封装在这个对象中。通过组装页面对象的操作来完成业务的封装。在编写测试用例时调用对应的业务完成测试即可。
二.搭建web框架结构
主要是围绕po模式来搭建结构
pages: 这是一个package,主要用来管理和存放页面对象的封装
actions:这是一个package,主要用来管理和存放业务的封装
testcases:这是一个package,主要用来管理和存放测试用例的封装
common: 这是一个package,主要用来管理和存放底层代码,比如driver的封装、日志封装、文
件封装
logs: 这是一个目录,存放日志文件的
data: 这是一个目录,存放测试数据的
report: 这是一个目录,存放测试结果以及测试报告的
video:这是一个目录,是测试过程中临时存放截图的
confifig: 这是一个目录,管理和存放配置信息
conftest.py: 主要是用例重写pytest的一些钩子函数的,以及自定义的fifixture函数
pytest.ini: pytest的基本配置文件
run.py: 整体框架的执行入口
get_project_path.py:主要是提供当前项目的目录路径
三.web自动化核心操作设计及封装
对于web自动来说driver对象是非常重要的,包括元素定位、点击、输入等等基本的操作,在这个框架都是核心的底层代码,因此我们首先需要封装这部分。在common目录下创建一个driver.py,在
driver.py中封装核心动作。
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions
from selenium.webdriver.support.wait import WebDriverWait
class InitDriver:
def __init__(self,browser='chrome'):
self.browser = browser.lower()
if self.browser == 'chrome':
self.driver = webdriver.Chrome()
elif self.browser == 'firefox':
self.driver = webdriver.Firefox()
elif self.driver =='ie':
self.driver = webdriver.Ie()
elif self.browser == 'edge':
self.driver = webdriver.Edge()
elif self.browser =='safari':
self.driver = webdriver.Safari()
else:
raise BaseException(f'不支持{self.browser}浏览器')
#窗口最大化
self.driver.maximize_window()
# 隐式等待
self.driver.implicitly_wait(10)
#请求网址封装
def get(self,url):
self.driver.get(url)
#封装find_element(),里面需要的(传参定位元素的方法,和定位元素的表达式)
def get_by(self,ele_info):
type = ele_info['type']
value = ele_info['value']
if type == 'id':
locator = (By.ID, value)
elif type == 'name':
locator = (By.NAME, value)
elif type == 'classname':
locator = (By.CLASS_NAME, value)
elif type == 'tagname':
locator = (By.TAG_NAME, value)
elif type == 'linktext':
locator = (By.LINK_TEXT, value)
elif type == 'partiallinktext':
locator = (By.PARTIAL_LINK_TEXT, value)
elif type == 'css':
locator = (By.CSS_SELECTOR, value)
elif type == 'xpath':
locator = (By.XPATH, value)
else:
raise BaseException(f'定位的类型【{type}】不支持')
return locator
#定位单元素
def find_element(self,ele_info):
name = ele_info['name']
type = ele_info['type'].lower()
value = ele_info['value']
timeout = ele_info['timeout']
# 获取定位元素的方式和表达式
locator = self.get_by(ele_info)
# 显示等待,返回元素的值
try:
wait = WebDriverWait(driver=self.driver,timeout=timeout)
element = wait.until(expected_conditions.presence_of_element_located(locator))
except BaseException as e:
raise BaseException(f'定位元素【{name}】,通过【{type}】方式,值是【{value}】,未定位到!')
return element
#定位多个元素
def find_elements(self,ele_info):
name = ele_info['name']
type = ele_info['type'].lower()
value = ele_info['value']
timeout = ele_info['timeout']
# 获取定位元素的方式和表达式
locator = self.get_by(ele_info)
# 显示等待,返回元素的值列表
try:
wait = WebDriverWait(driver=self.driver,timeout=timeout)
ele_list = wait.until(expected_conditions.presence_of_all_elements_located(locator))
except BaseException as e:
raise BaseException(f'定位元素【{name}】,通过【{type}】方式,值是【{value}】,未定位到!')
return ele_list
#封装点击方法
def click(self,ele_info):
name = ele_info['name']
type = ele_info['type'].lower()
value = ele_info['value']
timeout = ele_info['timeout']
# 获取定位元素的方式和表达式
locator = self.get_by(ele_info)
try:
wait = WebDriverWait(driver=self.driver,timeout=timeout)
wait.until(element_click_success(locator))
except BaseException as e:
raise BaseException(f'定位元素【{name}】,通过【{type}】方式,值是【{value}】,未定位到!')
#封装给输入框填充值的方法
def send_keys(self,ele_info,text):
element = self.find_element(ele_info)
element.send_keys(text)
#自己重写定义点击成功的方法
class element_click_success(object):
def __init__(self, locator):
self.locator = locator
def __call__(self, driver):
try:
element = driver.find_element(*self.locator)
element.click()
return element
except:
print('点击异常,继续轮休!')
return False
if __name__ == '__main__':
driver = InitDriver()
driver.get('https://blog.csdn.net/')
ele_list= {"name":"搜索框","type":"id","value":"toolbar-search-input","timeout":5}
driver.send_keys(ele_list,'Yasar.l')
ele_list = {"name": "搜索按钮", "type": "id", "value": "toolbar-search-button", "timeout": 5}
driver.click(ele_list)
四.POM模式脚本编写
登录page
from common.driver import InitDriver
class LoginPage:
def __init__(self, driver: InitDriver):
self.driver = driver
def send_keys_username(self):
ele_list = {"name": "用户名输入框", "type": "name", "value": "username", "timeout": 5}
self.driver.send_keys(ele_list, 'h2901')
def send_keys_password(self):
ele_list = {"name": "密码输入框", "type": "name", "value": "password","timeout":5}
self.driver.send_keys(ele_list,'E3s-uat2021!#')
def click_login_button(self):
ele_list = {"name": "登录按钮", "type": "xpath", "value": "//span[text()='登录']","timeout":5}
self.driver.click(ele_list)
if __name__ == '__main__':
loginPage = LoginPage(InitDriver())
loginPage.driver.get('https://XXXXXXXXXXXX.com/#/login')
loginPage.send_keys_username()
loginPage.send_keys_password()
loginPage.click_login_button()