1.pytest前后置(夹具)
作用:在用例执行之前和用例执行完之后,需要做的准备工作以及收尾工作,主要用于固定测试环境,以及清理回收
资源。
一般情况用例的定义有三种形式
- 类
class TestDemo:
# 类夹具:执行类中的用例之前操作
def setup_class(self):
print("类夹具执行之前输出的内容")
def test_3(self):
print("我是用例3")
# 一般用例脚本都使用实例方法,不建议使用类方法
@classmethod
def test_4(cls):
print("我是用例4")
# 类夹具:执行类中的用例之后操作
def teardown_class(self):
print("类夹具执行之后输出的内容")
- 方法
class Demo_001:
# 定义方法级别的夹具
def setup_method(self):
print("方法用例执行之前的操作")
def teardown_method(self):
print("方法用例执行之后的操作")
@pytest.mark.run(order=2)
def test_3(self):
print("我是用例300")
@classmethod
def test_4(cls):
print("我是用例400")
def test_5(self):
print("500")
def test_6(self):
print("600")
- 函数
def test_1():
print("我是用例1")
def test_2():
print("我是用例2")
def test_3():
print("我是用例3")
def test_4():
print("我是用例4")
# 使用函数级别的夹具
def setup_function():
print("函数用例之前的操作")
def teardown_function():
print("函数用例之后的操作")
模块级别的夹具
setup_module
teardown_module
当用例包中第一个用例开始执行出发前置,最后一个用例执行完毕之后执行后置
总结:
- 如果需要固定测试环境,可以针对不同类型的用例使用不同的夹具进行固化测试环境(前后置)
- 类,方法,函数并不一定非得前后置一起使用,可以只有前置或者只有后置也可以进行使用
2.pytest自定义夹具
使用fixture灵活调度固定的测试环境
fixture基本介绍
- 是pytest当中的一个装饰器
- @pytest.fixture(scope=“夹具的作用域”, params=“参数化”,autouse=“自动使用” )
- 通过fixture创建自定义的夹具
# 作用域:如果是function,针对当前模块所有的方法及函数自动调用
@pytest.fixture(scope="function", autouse=True)
def go_shop():
print("使用自动保持登录的id")
yield
print("保持登录号的用户id")
- 手动调用以及自动调用的区别及使用
import time
import pytest
# @pytest.mark.skip(reason="版本原因跳过该用例")
def test_1(go_shop):
print("我是用例1")
@pytest.mark.skipif(3 < 2, reason="反例不执行")
def test_2(go_shop):
# time.sleep(5)
print("我是用例2")
# print(1/0)
class TestDemo:
# 类夹具:执行类中的用例之前操作
def setup_class(self):
print("类夹具执行之前输出的内容")
def test_3(self,go_shop):
print("我是用例3")
# 一般用例脚本都使用实例方法,不建议使用类方法
@classmethod
def test_4(cls):
print("我是用例4")
# 类夹具:执行类中的用例之后操作
def teardown_class(self):
print("类夹具执行之后输出的内容")
# 作用域:如果是function,针对当前模块所有的方法及函数自动调用
# 如果使用默认的不进行自动调用的状态,那么可以进行手动使用
# 使用手动调用自定义夹具可以在需要执行的用例函数里面添加一个形参:fixture夹具名字
@pytest.fixture(scope="function", autouse=False)
def go_shop():
print("使用自动保持登录的id")
yield
print("保持登录号的用户id")
fixture作用域:
- function:针对函数和方法
方法或者函数执行之前及之后的前后置 - calss:针对类
类执行之前及之后的前后置 - module:针对模块
当前模块第一个用例执行之前及最后一个用例执行之后的前后置 - session:针对整个包
当用例包中第一个用例开始执行出发前置,最后一个用例执行完毕之后执行后置
3.fixture进行集中管理
整个项目中会定义一个模块:conftest.py专门用来放置自定义的fixture,文件名固定不能做修改。
不需要进行导包,就可以进行使用,不管是在根目录还是用例目录,以及模块目录都会被指定的作用域进行调用触发。
执行顺序:从最外面往最里面执行,从上到下,如果是同一个conftest.py模块那么会按照ASCII编码进行调用
4.使用测试框架管理用例
为了更加方便管理和使用用例的执行,那么会把用例定义成函数或者方法通过pytest进行管理
用例当中如果出现相同的代码需要进行独立封装,减少代码的冗余以及提高代码复用率
对用例需要进行测试环境的固定(前后置处理)
@pytest.fixture
def driver():
print("用例开始执行,获取驱动")
driver = Chrome()
yield driver
print("用例执行完毕,关闭驱动")
driver.quit()
5.保持登录状态
通过fixture夹具,把需要登录成功之后的投标流程用例进行区分
完成前台登录的前置任务(保持登录状态)
# 完成前台登录的前置任务(保持登录状态)
@pytest.fixture
def user_driver():
driver = Chrome()
driver.get("http://47.107.116.139/fangwei/")
driver.maximize_window()
# 1.实例化一个页面对象
rece_page = ReceptionLoginPage(driver)
# 2.通过对象调用实例方法用例脚本执行结果返回断言
msg = rece_page.login("admin", "msjy123")
print(msg)
return driver
def test_user_deal_ok(user_driver):
# 支付流程用例
rece_page = ReceptionLoginPage(user_driver)
msg = rece_page.pay(10000, "msjy123")
print(msg)
assert msg == "投标成功!"
# //*[@id="fanwe_success_box"]/table/tbody/tr/td[2]/div[2]
def test_user_deal_fail(user_driver):
# 支付流程用例
rece_page = ReceptionLoginPage(user_driver)
msg = rece_page.pay(10000, "9988")
print(msg)
assert msg == "支付密码错误"
# //*[@id="fanwe_error_box"]/table/tbody/tr/td[2]/div[2]
由于正例及反例元素定位值会发生变化,所以采用手写xpath方式进行元素定位
通过元素id以开头为参照进行定位
# - 获取提示信息断言实际结果
# text_pay_msg = (By.XPATH, '//*[@id="fanwe_success_box"]/table/tbody/tr/td[2]/div[2]')
text_pay_msg = (By.XPATH, '//*[starts-with(@id,"fanwe_")]/table/tbody/tr/td[2]/div[2]')
# 点击确定按钮关闭实际结果
btn_pay_ok = (By.XPATH, '//*[startswith(@
id,"fanwe_")]/table/tbody/tr/td[2]/div[3]/input[1]')
# //*[@id="fanwe_error_box"]/table/tbody/tr/td[2]/div[3]/input[1]