使用自定义ID函数

时间:2017-08-25 10:03:55

标签: python python-2.7 pytest fixtures

我有一个参数化测试,它将strdict作为参数,因此如果我允许pytest生成id,名称看起来很奇怪。

所以我虽然使用函数生成自定义ID,但它似乎没有按预期工作。

def id_func(param):
    if isinstance(param, str):
        return param


@pytest.mark.parametrize(argnames=('date', 'category_value'),
                         argvalues=[("2017.01", {"bills": "0,10", "shopping": "100,90", "Summe": "101,00"}),
                                    ("2017.02", {"bills": "20,00", "shopping": "10,00", "Summe": "30,00"})],
                         ids=id_func)
def test_demo(date, category_value):
    pass

我以为它会返回类似这样的东西

test_file.py::test_demo[2017.01] PASSED
test_file.py::test_demo[2017.02] PASSED

但它正在归还。

test_file.py::test_demo[2017.01-category_value0] PASSED
test_file.py::test_demo[2017.02-category_value1] PASSED

有人可以告诉我这有什么问题,还是有办法实现这个目标?

更新 我意识到问题是什么,将为每个参数调用if_func,如果我不为任何参数调用默认函数,我将不会返回str。我已经修好了,但那也很难看。

def id_func(param):
    if isinstance(param, str):
        return param
    return " "

现在它返回这样的内容,

test_file.py::test_demo[2017.01- ] PASSED
test_file.py::test_demo[2017.02- ] PASSED

问题是偶数如果我返回空字符串(即return ""),它将采用默认表示。有人能让我知道为什么吗?

2 个答案:

答案 0 :(得分:2)

一种方法是将argvalues移动到另一个变量,然后像这样编写测试:

import pytest


my_args = [
      ("2017.01", {"bills": "0,10", "shopping": "100,90", "Summe": "101,00"}),
      ("2017.02", {"bills": "20,00", "shopping": "10,00", "Summe": "30,00"})
]


@pytest.mark.parametrize(
    argnames=('date', 'category_value'), argvalues=my_args,
    ids=[i[0] for i in my_args]
)
def test_demo(date, category_value):
    pass

测试执行:

$ pytest -v tests.py 
================= test session starts =================
platform linux2 -- Python 2.7.12, pytest-3.2.1, py-1.4.34, pluggy-0.4.0 -- /home/kris/.virtualenvs/2/bin/python2
cachedir: .cache
rootdir: /home/kris/projects/tmp, inifile:
collected 2 items                                      

tests.py::test_demo[2017.01] PASSED
tests.py::test_demo[2017.02] PASSED

============== 2 passed in 0.00 seconds ===============

我认为使用函数(在您的情况下为idfn)是不可能的,因为如果它没有为对象生成标签,则使用默认的pytest表示。
查看pytest site了解详情。

答案 1 :(得分:0)

或者,您也可以使用列表推导来生成您的ID,如下所示:

import pytest


values = [
    ("2017.01", {"bills": "0,10", "shopping": "100,90", "Summe": "101,00"}),
    ("2017.02", {"bills": "20,00", "shopping": "10,00", "Summe": "30,00"})
]
value_ids = [e[0] for e in values]


@pytest.mark.parametrize('date,category_value', values, ids=value_ids
)
def test_demo(date, category_value):
    pass

假设这些测试位于目录根目录的test_file.py中,如果运行pytest test_file.py --co -q,将得到以下输出:

test_file.py::test_demo[2017.01]
test_file.py::test_demo[2017.02]