web-dev-qa-db-ja.com

pytestがフィクスチャを見つける方法と場所

Py.testはフィクスチャをどこでどのように探しますか?同じフォルダの2つのファイルに同じコードがあります。 conftest.pyを削除すると、cmdoptがtest_conf.pyを実行しているのを見つけることができません(同じフォルダーにあります。sonoftest.pyが検索されないのはなぜですか?)

# content of test_sample.py
def test_answer(cmdopt):
    if cmdopt == "type1":
        print ("first")
    Elif cmdopt == "type2":
        print ("second")
    assert 0 # to see what was printed

conftest.pyの内容

import pytest

def pytest_addoption(parser):
    parser.addoption("--cmdopt", action="store", default="type1",
        help="my option: type1 or type2")

@pytest.fixture
def cmdopt(request):
    return request.config.getoption("--cmdopt")

sonoftest.pyのコンテンツ

import pytest

def pytest_addoption(parser):
    parser.addoption("--cmdopt", action="store", default="type1",
        help="my option: type1 or type2")

@pytest.fixture
def cmdopt(request):
    return request.config.getoption("--cmdopt")

ドキュメントは言う

http://pytest.org/latest/fixture.html#fixture-function

  1. pytestは、test_プレフィックスがあるため、test_ehloを検出します。テスト関数には、smtpという名前の関数引数が必要です。一致するフィクスチャ関数は、smtpという名前のフィクスチャが付けられた関数を探すことによって発見されます。
  2. smtp()は、インスタンスを作成するために呼び出されます。
  3. test_ehlo()が呼び出され、テスト関数の最終行で失敗します。
33
Dave

py.testはconftest.pyとすべてのPythonファイル、python_filesパターンに一致します。デフォルトではtest_*.pyです。テストフィクスチャがある場合、 conftest.pyから、またはそれに依存するテストファイルからインポートまたはインポートするには:

from sonoftest import pytest_addoption, cmdopt
31
ecatmur

以下は、py.testがフィクスチャ(およびテスト)を探す順序と場所です(- here から取得):

py.testは、ツールの起動時に次の方法でプラグインモジュールをロードします。

  1. すべての組み込みプラグインをロードする

  2. setuptoolsエントリポイントを通じて登録されたすべてのプラグインをロードする。

  3. -p nameオプションのコマンドラインを事前スキャンし、実際のコマンドライン解析の前に指定されたプラグインをロードする。

  4. コマンドラインの呼び出しで推測されたすべてのconftest.pyファイルをロードする(テストファイルとそのすべての親ディレクトリ)。サブディレクトリのconftest.pyファイルは、デフォルトではツールの起動時にロードされないことに注意してください。

  5. conftest.pyファイルのpytest_plugins変数で指定されたすべてのプラグインを再帰的にロードする

19
Alex Okrushko

私は同じ問題を抱えており、簡単な解決策を見つけるために多くの時間を費やしました。この例は、私と同じような状況にある他の人のためのものです。

  • conftest.py:
import pytest

pytest_plugins = [
 "some_package.sonoftest"
]

def pytest_addoption(parser):
  parser.addoption("--cmdopt", action="store", default="type1",
      help="my option: type1 or type2")

@pytest.fixture
def cmdopt(request):
  return request.config.getoption("--cmdopt")
  • some_package/sonoftest.py:
import pytest

@pytest.fixture
def sono_cmdopt(request):
  return request.config.getoption("--cmdopt")
  • some_package/test_sample.py
def test_answer1(cmdopt):
  if cmdopt == "type1":
      print ("first")
  Elif cmdopt == "type2":
      print ("second")
  assert 0 # to see what was printed

def test_answer2(sono_cmdopt):
  if sono_cmdopt == "type1":
      print ("first")
  Elif sono_cmdopt == "type2":
      print ("second")
  assert 0 # to see what was printed

ここで同様の例を見つけることができます: https://github.com/pytest-dev/pytest/issues/3039#issuecomment-464489204 と他のここ https://stackoverflow.com/a/54736376/6655459

公式のpytestドキュメントの説明: https://docs.pytest.org/en/latest/reference.html?highlight=pytest_plugins#pytest-plugins

pytestによってプラグインをロードするには、some_package.test_sample"で参照されるそれぞれのディレクトリに__init__.pyファイルが必要であることに注意してください。

1
rafalkasa