#python #pytest
Вопрос:
Я передаю файл json со следующим:
#config.json
[
{
"id" : 1,
"description" : "test1",
"data1": [1, 2, 3],
"data2": ["foo", "bar", "baz"]
},
{
"id" : 2,
"description" : "test2",
"data1": [4, 5, 6],
"data2": ["baz", "foo"]
}
]
Попытка использовать data1 для создания тестовых перестановок. Самый элементарный способ вызвать проблему-это:
#######################
# conftest.py
import json
import pathlib
import pytest
def pytest_generate_tests(metafunc):
print("pytest_generate_tests")
config = pathlib.Path(metafunc.module.__file__).with_name('config.json')
testdata = json.loads(config.read_text())
for test in testdata:
metafunc.parametrize('testdata', testdata)
metafunc.parametrize('data', test.get('data1'))
#######################
#test_example.py
import pytest
def test_example(testdata, data):
pass
Что приводит к ошибке:
external_data/conftest.py:11: in pytest_generate_tests
metafunc.parametrize('data', test.get('data1'))
/usr/local/lib/python3.9/site-packages/pytest-6.2.3-py3.9.egg/_pytest/python.py:1100: in parametrize
newcallspec.setmulti2(
/usr/local/lib/python3.9/site-packages/pytest-6.2.3-py3.9.egg/_pytest/python.py:932: in setmulti2
self._checkargnotcontained(arg)
/usr/local/lib/python3.9/site-packages/pytest-6.2.3-py3.9.egg/_pytest/python.py:909: in _checkargnotcontained
raise ValueError(f"duplicate {arg!r}")
E ValueError: duplicate 'data'
Что я хотел бы видеть, так это то, что обе более широкие структуры будут проверены на все перестановки данных 1 (и, в конечном счете, данных 2)
external_data/test_example.py::test_example[testdata0-1] PASSED
external_data/test_example.py::test_example[testdata0-2] PASSED
external_data/test_example.py::test_example[testdata0-3] PASSED
external_data/test_example.py::test_example[testdata1-4] PASSED
external_data/test_example.py::test_example[testdata1-5] PASSED
external_data/test_example.py::test_example[testdata1-6] PASSED
Ответ №1:
Вы должны передать список для параметризации, иначе вы просто вызываете parametrize('data',...)
несколько раз с разными аргументами.
Что — то вроде этого должно сработать:
def pytest_generate_tests(metafunc):
print("pytest_generate_tests")
config = pathlib.Path(metafunc.module.__file__).with_name('config.json')
testdata = json.loads(config.read_text())
data = [test.get('data') for test in testdata]
metafunc.parametrize('data', data)
параметризация принимает итерацию в качестве второго аргумента.
Комментарии:
1. данные становятся списком списков [[1,2,3],[4,5,6]].
test.get('data1')
возвращает повторяющийся список.