官方pytest文档:Full pytest documentation — pytest documentation


一、pytest以及辅助插件的安装

1、pytest安装

pip install pytest

2、辅助插件及介绍

pytest-html(生成htm报告的插件)
pytest-xdist (多线程运行的插件)
pytest-ordering (改变用例的执行顺序的插件)
pytest-rerunfailres (失败用例重跑的插件)
allure-pytest (生成美观自定义的allure报告)pytest test_*.py --alluredir=result + allure serve result
        allure generate --alluredir=result -o report/ --clean
pytest-rerunfailures (失败重跑插件)
pytest-repeat   (重复执行用例的插件)
pytest-assume  (assume多重断言,断言失败后边的代码会继续执行)

//插件太多,可通过pip install -r pludin.txt一次性下载完成
例如:plugin.txt中内容如下
pytest-html
pytest-xdist
终端运行:pip install -r pugin.txt即可下载这两个插件

3、安装插件报错

1)下面是没有安装相应插件报错,例:没有安装allure-pytest插件,运行pytest --alluredir=./temp 会报此错

ERROR: usage: run.py [options] [file_or_dir] [file_or_dir] [...]
run.py: error: unrecognized arguments: --alluredir=./reports/temp/ --clean-alluredir
inifile: C:\Users\EDY\PycharmProjects\ProductAuto\pytest.ini
rootdir: C:\Users\EDY\PycharmProjects\ProductAuto

二、pytest运行

测试套件默认规则:测试文件必须以test_*开头,测试类名字必须是Test*开头,测试方法名字必须是test_*开头,否则运行时会找不到测试套件

pytest命令的参数:

-vs        输出详细信息。输出调试信息。如: pytest -vs
-n      多线程运行。( 前提安装插件: pytest-xdist)如: pytest -VS -n=2
--reruns 失败重跑(前提安装插件: pytest-rerunfailres )如: pytest --reruns=2
   raise Exception()抛出异常,try except解决异常。
-x     出现一个用例失败则停止测试。如: pytest -x
--maxfail 出现几个失败才终止,如: pytest --maxfail=2
--html   生成html的测试报告(前提安装插件: pytest-html) , 如: pytest --html=report/report.html
-k     运行测试用例名称中包含某个字符串的测试用例。
-m     只测试被标记的用例
--strict-markers 未在pytest.ini配置文件注册的标记mark都会引发报错
--reruns n  (安装pytest-rerunfailures插件),失败重跑n次,最大运行次数n pytest --reruns 5
--reruns-delay n )(pytest-rerunfailures插件),pytest --rerun 2 --reruns-delay 5 失败重跑之间间隔5s
--count    重复执行测试,需安装pytest-repeat,使用:pytest --count=5或者pytest --count 5
        重复执行所有测试用例5次,主要结合-x使用,测试偶发bug,运行直到执行失败
        还有@pytest.mark.repeat(n)可对测试类、方法使用

有两种执行方式:

1)命令行运行:pytest -vs -x

2)主函数运行:

if __name__ == "__main__":
pytest.main(["-vs”,“-x"])

指定运行:

pytest  test_*.py    //运行指定的test_*.py ,多个py文件分号隔开
pytest testcase/ //运行指定的testcase目录下所有测试文件
pytest -k "cs” //测试包含有“cs”的测试类和方法
pytest testcase/test_*.py::Test_lei::test_* //可具体指定某个方法

测试执行结果:

  • 退出code 0: 收集并成功通过所有测试用例
  • 退出code 1: 收集并运行了测试,部分测试用例执行失败
  • 退出code 2: 测试执行被用户中断
  • 退出code 3: 执行测试中发生内部错误
  • 退出code 4: pytest命令行使用错误
  • 退出code 5: 没有收集到测试用例

全局配置文件pytest.ini,一般建在项目根目录下

注意:

1)这个配置文件的名称不能改

2)编码格式是ANSI,写入中文后自动变为GB2312 中文简体

3)pytest.main()会带上其中配置的参数

pytest.ini配置文件内容解释,实际中根据需求可选择性添加配置。

[pytest]

//pytest参数配置
addopts = -VS

//需要执行用例模块目录
testpaths =./testcases

//可更改测试文件、类、方法的默认规则,一般不做更改
python_files = test_*.py
python_classes = Test*
python_functions = test_*

//标记用例,一般用于冒烟测试,以下的smoke是标签名,”冒烟测试“是描述,使用
markers=
  smoke:"冒烟测试"
  flow:"流水"

//与@pytest.mark.xfail()的strict一样,为False,意外pass的结果显示xpass,为True,则显示Failed
xfail_strict = False

//控制台日志输出控制器,为True输出,为False关闭
log_cli = True

//用来加速收集用例,去掉不要谝历的目录
norecursedirs = * (目录)

断言类型

1)assert正常断言

def test_001(self):  
   assert var==3  //判断var等于3
   assert var in ‘ab’  //判断字符串‘ab’包含var
   assert var is False  //判断var 为假
   assert var not True  //判断var不为真
   assert var  //判断var为真

2)pytest.raise()异常断言

def test_002(self):
with pytest.raises(ZeroDivisionError):
1/0

3)pytest.warns()警示断言

暂没有合适例子

临时目录

1)项目运行过程中,总会产生一些临时文件,pytest提供了tmp_path来创建临时目录。

tmp_path是一个pathlib/pathlib2.Path对象。以下是测试使用方法的示例如:

# test_tmp_path.py文件内容
import os CONTENT = u"content" def test_create_file(tmp_path):
d = tmp_path / "sub"
d.mkdir()
p = d / "hello.txt"
p.write_text(CONTENT)
assert p.read_text() == CONTENT
assert len(list(tmp_path.iterdir())) == 1
assert 0

测试结果如下:除了assert0以外,其他都断言成功
_____________________________ test_create_file _____________________________ tmpdir = local('PYTEST_TMPDIR/test_create_file0') def test_create_file(tmpdir):
p = tmpdir.mkdir("sub").join("hello.txt")
p.write("content")
assert p.read() == "content"
assert len(tmpdir.listdir()) == 1
> assert 0
E assert 0

2)tmpdir_factory

四、前置和后置

前置和后置方法如下:

  • 模块级别:setup_module、teardown_module
  • 函数级别:setup_function、teardown_function,不在类中的方法
  • 类级别:setup_class、teardown_class
  • 方法级别:setup_method、teardown_method
  • 方法细化级别:setup、teardown
def setup_module():
print("=====整个.py模块开始前只执行一次:打开浏览器=====") def teardown_module():
print("=====整个.py模块结束后只执行一次:关闭浏览器=====") def setup_function():
print("===每个函数级别用例开始前都执行setup_function===") def teardown_function():
print("===每个函数级别用例结束后都执行teardown_function====") def test_one():
print("one") class TestCase():
def setup_class(self):
print("====整个测试类开始前只执行一次setup_class====") def teardown_class(self):
print("====整个测试类结束后只执行一次teardown_class====") def setup_method(self):
print("==类里面每个用例执行前都会执行setup_method==") def teardown_method(self):
print("==类里面每个用例结束后都会执行teardown_method==") def setup(self):
print("=类里面每个用例执行前都会执行setup=") def teardown(self):
print("=类里面每个用例结束后都会执行teardown=") def test_three(self):
print("two")

五、fixtrue实现前后置

@pytest.fixtrue(scope="xxx")和yeild实现前置和后置

1)参数scope的五个范围级别:fuction(默认)、class、module、package、session,实例化顺序级别从右至左

2)类调用fixtrue固件只能通过@pytest.mark.usefixtrues("aaa","bbb"),aaa和bbb均为函数名

3)方法能通过参数调用,如def aaa(bbb),aaa为调用函数,bbb为固件函数名,也能使用@pytest.mark.usefixtrues("aaa","bbb")调用

具体效果如下:

//不调用则不显示
@pytest.fixture()
def ttt():
print("fuction-setup4") @pytest.fixture()
def aaa():
print("fuction-setup1") @pytest.fixture()
def bbb():
print("fuction-setup2") @pytest.fixture(scope="class")
def ccc():
print("setup") //调用程序前执行
yield //后面的的方法体相当于后置
print("teardown") //调用程序后执行 //类调用fuction范围级别固件bbb,相当于类里面的每个方法都调用bbb
@pytest.mark.usefixtures("bbb")
//类调用class级别固件ccc,只在调用的类前执行一次
@pytest.mark.usefixtures("ccc")
class Test_study: def test_ddd(self,aaa): //先bbb输出,再aaa输出
print("AAAAAA") @pytest.mark.smoke
def test_eee(self):
print("BBBBBB") -------------------结果如下-------------------------------- kuadi/test_kuadi_login.py::Test_study::test_ddd setup
fuction-setup2
fuction-setup1
AAAAAA
PASSED
kuadi/test_kuadi_login.py::Test_study::test_eee fuction-setup2
BBBBBB
PASSEDteardown

4)其他调用情况

@pytest.fixture(scope="class")
def aaa():
print("aaa_start")
yield
print("aaa_end") @pytest.fixture()
def bbb():
print("bbb_start")
yield
print("bbb_end") @pytest.mark.usefixtures("bbb")
def test_fff():
print("fff") class Test_QQQ:
@pytest.mark.usefixtures("bbb")
def test_ccc(self):
print("ccc") def test_ddd(self, aaa):
print("ddd") def test_eee(self):
print("eee") 结果------------
fds.py::test_fff bbb_start
fff
PASSEDbbb_end fds.py::Test_QQQ::test_ccc bbb_start
ccc
PASSEDbbb_end fds.py::Test_QQQ::test_ddd aaa_start
ddd
PASSED
fds.py::Test_QQQ::test_eee eee
PASSEDaaa_end

5)yield和addfinalizer函数的使用

//yield配合fixtrue实现前后置方法
@pytest.fixture(scope="class")
def ccc():
print("setup")
yield
print("teardown") //with配合yield,等待测试完成后,自动关闭连接
@pytest.fixture(scope="module")
def smtp_connection():
with smtplib.SMTP("smtp.gmail.com", 587, timeout=5) as smtp_connection:
yield smtp_connection //通过后置操作在测试完成后关闭浏览器连接
@pytest.fixture(scope="module")
def test_addfinalizer(request):
# 前置操作setup
print("==再次打开浏览器==")
test = "test_addfinalizer" def fin():
# 后置操作teardown
print("==再次关闭浏览器==") request.addfinalizer(fin)
# 返回前置操作的变量
return test

六、conftest文件

conftest文件注意事项:

  • pytest会默认读取conftest.py里面的所有fixture,所以不用导入fixtrue
  • conftest.py 文件名称是固定的,不能改动
  • conftest.py中fixtrue只对同一个package下的所有测试用例生效,其他目录中引入会报错not found
  • 不同目录可以有自己的conftest.py,一个项目中可以有多个conftest.py
  • 下级目录的conftest中fixtrue可以覆盖重写上级目录中同名的fixtrue,且就近生效
  • 测试用例文件中不需要手动import conftest.py,pytest会自动查找

七、参数化

@pytest.mark.parametrize()

官方文档:How to parametrize fixtures and test functions — pytest documentation

用法如下:

//测试方法和函数使用
@pytest.mark.parametrize("test_input,expected", [("3+5", 8), ("2+4", 6), ("6*9", 42)])
def test_eval(test_input, expected):
assert eval(test_input) == expected
//测试类使用
@pytest.mark.parametrize("n,expected", [(1, 2), (3, 4)])
class TestClass:
def test_simple_case(self, n, expected):
assert n + 1 == expected def test_weird_simple_case(self, n, expected):
assert (n * 1) + 1 == expected
//模块全局使用
pytestmark = pytest.mark.parametrize("n,expected", [(1, 2), (3, 4)]) class TestClass:
def test_simple_case(self, n, expected):
assert n + 1 == expected
//mark标记使用
@pytest.mark.parametrize(
"test_input,expected",
[("3+5", 8), ("2+4", 6), pytest.param("6*9", 42, marks=pytest.mark.xfail)],
)
def test_eval(test_input, expected):
assert eval(test_input) == expected
//叠加使用
@pytest.mark.parametrize("x", [0, 1])
@pytest.mark.parametrize("y", [2, 3])
def test_foo(x, y):
print({x},{y}) 结果按顺序:0,2/1,2/0.3/1,3

@pytest.fixtrue()

第一个例子
# content of conftest.py
import pytest
import smtplib @pytest.fixture(scope="module", params=["smtp.gmail.com", "mail.python.org"])
def smtp_connection(request):
smtp_connection = smtplib.SMTP(request.param, 587, timeout=5)
yield smtp_connection
print("finalizing {}".format(smtp_connection))
smtp_connection.close()
//第二个例子
@pytest.fixture(params=[0, 1], ids=["spam", "ham"])
def a(request):
return request.param def test_a(a):
pass def idfn(fixture_value):
if fixture_value == 0:
return "eggs"
else:
return None @pytest.fixture(params=[0, 1], ids=idfn)
def b(request):
return request.param def test_b(b):
pass 结果-------------------------------------------------
<Function test_a[spam]>
<Function test_a[ham]>
<Function test_b[eggs]>
<Function test_b[1]>

@pytest.fixtrue带标记

@pytest.fixture(params=[0, 1, pytest.param(2, marks=pytest.mark.skip)])
def data_set(request):
return request.param def test_data(data_set):
pass

fixtrue中使用fixtrue:smtp_connection()是第一个用例中fixtrue

class App:
def __init__(self, smtp_connection):
self.smtp_connection = smtp_connection @pytest.fixture(scope="module")
def app(smtp_connection):
return App(smtp_connection) def test_smtp_connection_exists(app):
assert app.smtp_connection

按fix true实例自动对测试进行分组

@pytest.fixture(scope="module", params=["mod1", "mod2"])
def modarg(request):
param = request.param
print(" SETUP modarg", param)
yield param
print(" TEARDOWN modarg", param) @pytest.fixture(scope="function", params=[1, 2])
def otherarg(request):
param = request.param
print(" SETUP otherarg", param)
yield param
print(" TEARDOWN otherarg", param) def test_0(otherarg):
print(" RUN test0 with otherarg", otherarg) def test_1(modarg):
print(" RUN test1 with modarg", modarg) def test_2(otherarg, modarg):
print(" RUN test2 with otherarg {} and modarg {}".format(otherarg, modarg)) --------------------------------结果-------------------------------
collecting ... collected 8 items test_module.py::test_0[1] SETUP otherarg 1
RUN test0 with otherarg 1
PASSED TEARDOWN otherarg 1 test_module.py::test_0[2] SETUP otherarg 2
RUN test0 with otherarg 2
PASSED TEARDOWN otherarg 2 test_module.py::test_1[mod1] SETUP modarg mod1
RUN test1 with modarg mod1
PASSED
test_module.py::test_2[mod1-1] SETUP otherarg 1
RUN test2 with otherarg 1 and modarg mod1
PASSED TEARDOWN otherarg 1 test_module.py::test_2[mod1-2] SETUP otherarg 2
RUN test2 with otherarg 2 and modarg mod1
PASSED TEARDOWN otherarg 2 test_module.py::test_1[mod2] TEARDOWN modarg mod1
SETUP modarg mod2
RUN test1 with modarg mod2
PASSED
test_module.py::test_2[mod2-1] SETUP otherarg 1
RUN test2 with otherarg 1 and modarg mod2
PASSED TEARDOWN otherarg 1 test_module.py::test_2[mod2-2] SETUP otherarg 2
RUN test2 with otherarg 2 and modarg mod2
PASSED TEARDOWN otherarg 2
TEARDOWN modarg mod2

测试功能不需要直接访问fixtrue时,如建一个临时目录或者文件供测试使用,结合@pytest.markusefixtrues()

# content of conftest.py 

import os
import tempfile import pytest @pytest.fixture
def cleandir():
with tempfile.TemporaryDirectory() as newpath:
old_cwd = os.getcwd()
os.chdir(newpath)
yield
os.chdir(old_cwd) ------------------------------------
# content of test_setenv.py
import os
import pytest @pytest.mark.usefixtures("cleandir")
class TestDirectoryInit:
def test_cwd_starts_empty(self):
assert os.listdir(os.getcwd()) == []
with open("myfile", "w") as f:
f.write("hello") def test_cwd_again_starts_empty(self):
assert os.listdir(os.getcwd()) == []
//其他用法
@pytest.mark.usefixtures("cleandir", "anotherfixture") 指定多个fix true
def test():
pass //使用pytestmark在测试模块级别指定夹具的用途
pytestmark = pytest.mark.usefixtures("cleandir") //将项目中所有测试所需的夹具放入ini文件中
[pytest]
usefixtures = cleandir

结合@pytest.mark.parametrize()使用,fixtrue作测试数据处理功能,如:factory

@pytest.fixture(scope="function")
def input_user(request):
user = request.param
print("登录账户:%s" % user)
return user @pytest.fixture(scope="function")
def input_psw(request):
psw = request.param
print("登录密码:%s" % psw)
return psw name = ["name1", "name2"]
pwd = ["pwd1", "pwd2"] @pytest.mark.parametrize("input_user", name, indirect=True)
@pytest.mark.parametrize("input_psw", pwd, indirect=True)
def test_more_fixture(input_user, input_psw):
print("fixture返回的内容:", input_user, input_psw)

fixtrue会覆盖同名的fixtrue

tests/
__init__.py conftest.py
# content of tests/conftest.py
import pytest @pytest.fixture(params=['one', 'two', 'three']) //最初的参数化fixtrue
def parametrized_username(request):
return request.param @pytest.fixture  //最初的非参数化fixtrue
def non_parametrized_username(request):
return 'username' test_something.py
# content of tests/test_something.py
import pytest @pytest.fixture  //非参数化fixtrue覆盖参数化fixtrue
def parametrized_username():
return 'overridden-username'

     //参数化fixtrue覆盖非参数化fixtrue
@pytest.fixture(params=['one', 'two', 'three'])
def non_parametrized_username(request):
return request.param def test_username(parametrized_username):
assert parametrized_username == 'overridden-username' def test_parametrized_username(non_parametrized_username):
assert non_parametrized_username in ['one', 'two', 'three'] test_something_else.py
# content of tests/test_something_else.py
def test_username(parametrized_username):
assert parametrized_username in ['one', 'two', 'three'] def test_username(non_parametrized_username):
assert non_parametrized_username == 'username'

直接参数化的fixtrue覆盖非参数化fixtrue

//直接参数化也可以覆盖fixtrue
tests/
__init__.py conftest.py
# content of tests/conftest.py
import pytest @pytest.fixture
def username():
return 'username' test_something.py
# content of tests/test_something.py
import pytest @pytest.mark.parametrize('username', ['directly-overridden-username'])
def test_username(username):
assert username == 'directly-overridden-username'

八、其他装饰器

官方API Reference — pytest documentation

1、@pytest.mark.xfail()、pytest.xfail

@pytest.mark.xfail(condition,*,reason=none,raises=none,run=True,strict=False)

1)raises:none表示默认匹配所有异常错误,值为type(Exception),只能是异常值

2)condition:boolea or str类型,就是有条件执行,只跳过部分特殊用例时使用

3)run:为true,该怎么样就怎么样,为False,则该测试套件不会运行,且始终标为xfail

4)reson:原因说明

5)strict:为False,用例通过显示xpass,用例失败显示xfail,为True,用例失败显示xfail,用例意外通过则显示fail

函数、方法、类执行前使用@pytest.mark.xfail(),预期失败

对方法使用:

//raises参数为空或者与所报的错误匹配时结果是xfail,此结果是预期失败,说明用例通过
@pytest.mark.xfail()
def test_002(self):
print("账户修改")
raise Exception //raises参数与所报的错误不匹配时结果是failed
@pytest.mark.xfail(raises=ZeroDivisionError)
def test_004(self):
print("账户修改")
raise Exception --------------------结果------------------------ test_interface.py::Test_kuaidi::test_002 账户修改
XFAIL
test_interface.py::Test_kuaidi::test_004 账户修改
FAILED

对类使用:

@pytest.mark.xfail(raises=ZeroDivisionError)
class Test_kuaidi: def test_002(self): //不匹配的用例显示failed
print("账户修改")
raise Exception def test_004(self): //xpass,意外通过
print("账户修改")
# raise Exception def test_005(self): //匹配的用例显示xfail
1/0 ------------------------结果展示--------------- test_interface.py::Test_kuaidi::test_002 账户修改
FAILED
test_interface.py::Test_kuaidi::test_004 账户修改
XPASS
test_interface.py::Test_kuaidi::test_005 XFAIL

pytest.xfail(reason=none),主要使用来对已知错误和功能缺失使用的,使用例子:

def test_aaa():
pytest.xfail(reason="功能未做") ---------结果------------------------- test_interface.py::test_aaa XFAIL (功能未做)

2、@pytest.mark.skip()、@pytest.mark.skipif()、pytest.skip、pytest.importorskip

都是跳过用例,区别:

@pytest.mark.skip(reason=None):reason跳过的原因,不影响程序运行

@pytest.mark.skipif(condition, reason=None):condition参数的值只能是Boolean或者str,有条件跳过

@pytest.mark.skip使用在测试类、测试方法、测试函数上,则测试类、测试方法、测试函数中所有用例都会跳过

@pytest.mark.skipif使用在测试类、测试方法、测试函数上,condition有值则根据条件跳过,没有值和@pytest.mark.skip一样

@pytest.mark.skipif(sys.platform == 'win32', reason="does not run on windows")
class TestSkipIf(object):
def test_function(self):
print("不能在window上运行")

pytest.skip(reason=none,allow_module_level=False,msg)

allow_module_level:默认为False,为True则会允许模块调用,执行时会跳过模块中剩余的用例

def test_aaa():
pytest.skip("功能未做") //注意,pytest.skip(reason="功能未做")会报错 结果:test_interface.py::test_aaa SKIPPED (功能未做) pytest.skip(r"功能未做",allow_module_level=True) 结果:跳过所有剩余用例

pytest.importorskip(modname,minversion=none,reason=none)

作用:缺少导入包,跳过用例测试

参数:modname,导入的模块名;minversion,模块最小版本号

expy = pytest.importorskip("pytest", minversion="7.0",reason="pytest7.0版本没有出来")

@expy
def test_import():
print("test")
结果:会跳过所有该模块的用例测试

3、@pytest.mark.flaky()

前提安装pytest-rerunfailures,reruns:重跑次数,reruns_delay:重跑间隔时间

禁止:1、不能和@pytest.fixtrue()一起使用

   2、该插件与pytest-xdist的looponfail不兼容

   3、与核心--pdb标志不兼容

    @pytest.mark.flaky(reruns=2,reruns_delay=5)
def test_ddd(self):
assert False ---------------------执行结果-------------------------
kuadi/test_kuadi_login.py::Test_study::test_ddd RERUN
kuadi/test_kuadi_login.py::Test_study::test_ddd RERUN
kuadi/test_kuadi_login.py::Test_study::test_ddd FAILED

九、hooks函数

学习地址:Pytest权威教程21-API参考-04-钩子函数(Hooks) - 韩志超 - 博客园 (cnblogs.com)

pytest学习总结的更多相关文章

  1. [转载]pytest学习笔记

    pytest学习笔记(三)   接着上一篇的内容,这里主要讲下参数化,pytest很好的支持了测试函数中变量的参数化 一.pytest的参数化 1.通过命令行来实现参数化 文档中给了一个简单的例子, ...

  2. Pytest学习(三) - setup和teardown的使用

    一.前言 从文章标题可以看出,就是初始化和释放的操作,根据我的java习惯来学习pytest,个人感觉没差太多,理解上也不是很难. 哦,对了,差点跑题了,这个框架是基于Python语言的,在学习的时候 ...

  3. pytest学习笔记

    From: https://blog.csdn.net/gaowg11/article/details/54910974 由于对测试框架了解比较少,所以最近看了下pytest测试框架,对学习心得做个记 ...

  4. pytest 学习笔记一 入门篇

    前言 之前做自动化测试的时候,用的测试框架为Python自带的unittest框架,随着工作的深入,发现了另外一个框架就是pytest (官方地址文档http://www.pytest.org/en/ ...

  5. pytest学习笔记(一)

    这两天在学习pytest,之前有小用到pytest,觉得这个测试框架很灵巧,用在实现接口自动化(pytest+requests)非常的轻便,然后很有兴致的决定学习下,然后又发现了pytest-sele ...

  6. Pytest学习(一)- 入门及基础

    前言 十一也赶上自己刚出院,本想在十一放假前用假期刷完Pytest的,结果被希洛克神话吸引,再次回归毒奶粉,一直奋斗到距离上班还有两天,引导石刷没了,就没了智慧. 当然也没出过神话,结果一怒之下卸载, ...

  7. Pytest学习(二) - 断言的使用

    一.前言 学习pytest总会习惯性的和unittest对比使用,自然就断言pytest和unittest也是有些区别的. 二.断言对比 unittest 断言 assertEqual(a, b) # ...

  8. Pytest学习笔记3-fixture

    前言 个人认为,fixture是pytest最精髓的地方,也是学习pytest必会的知识点. fixture用途 用于执行测试前后的初始化操作,比如打开浏览器.准备测试数据.清除之前的测试数据等等 用 ...

  9. pytest学习笔记(三)

    接着上一篇的内容,这里主要讲下参数化,pytest很好的支持了测试函数中变量的参数化 一.pytest的参数化 1.通过命令行来实现参数化 文档中给了一个简单的例子, test_compute.py ...

  10. pytest学习笔记(二)

    继续文档的第二章 (一)pytest中可以在命令行中静态/动态添加option,这里没什么好讲的,略过... 这里面主要讲下如何试用skip/xfail,还有incremental(包含一些列的测试步 ...

随机推荐

  1. JZOJ 3207.Orthogonal Anagram

    \(\text{Problem}\) 给出一个字符串,求经过重新排列的另一个字典序最小的字符串,满足:相同的位置上 原串与结果串的字符不同.不存在则输出空串. \(\text{Solution}\) ...

  2. 基于Docker部署Dubbo+Nacos服务

    一.说明 本文介绍基于 Docker 部署一套 Dubbo + Nacos 的微服务环境,并解决容器里的 IP 及端口的访问问题. 基于上文<基于jib-maven-plugin快速构建微服务d ...

  3. ArcGIS for Android 地图图文查询

    ArcGIS for Android 地图图文查询 1.前期项目准备 1.1. 创建新工程 新建一个空活动项目 选择语言.平台,修改命名等 1.2. 添加ArcGIS SDK build.gradle ...

  4. 【博图scl语言】313-2dp

    ①如果 if(***) then *** := ***; end_if; ②循环 for n1:=1 to 50 by 1 do end_for; WHILE #n1 < 54 DO END_W ...

  5. element-ui的collapse中嵌套table表格 的 高度跳跃 问题

    <script src="//unpkg.com/vue@2.6.10/dist/vue.js"></script><script src=" ...

  6. tasklist

    tasklist是windows下列出进程信息的指令,可配合taskKill来关毕进程 https://learn.microsoft.com/zh-cn/windows-server/adminis ...

  7. 页面导出为PDF

    一.使用环境 Vue3.Quasar.Electron 二.安装 jspdf-html2canvas npm install jspdf-html2canvas --save 安装失败可以选择cnpm ...

  8. Bugku-ez_misc[wp]

    题目描述 1.拿到一份abc.rar文件,里面有一个加密call.png (1)通过file  . binwalk . 伪加密一顿小输出都不行,于是放进16进制编辑器查看: 文件头不对! (2)修改为 ...

  9. vue 使用mixin

    mixin 混入 混入提供了一种非常灵活的方式,来分发Vue组件中可以复用的功能,一个混入对象可以包括任意的组件选项,当组件使用混入对象时,所有的混入对象的选项 将被'混合'进入该组件本身的选项,混入 ...

  10. Launchpad是什么?Launchpad使用教程

    ​ Launchpad是什么?Launchpad 是用来查找和打开Mac系统下的 app 的最快捷方式,通过 Launchpad,您可以查看.整理并轻松打开Mac里面几乎所有的应用软件.下面带来Mac ...