Seleniumでpytestを使用してWebサイトを自動化しています。テストケースが失敗した場合にのみスクリーンショットを撮りたいです。私は以前にTestNGを使用しましたが、TestNGではITestListnerを使用するのはかなり東です。 pytestでそのようなものがありますか?.
私はteardown_method()を使用してこれを達成しようとしましたが、テストケースが失敗したときにこのメソッドは実行されません。
_import sys
from unittestzero import Assert
class TestPY:
def setup_method(self, method):
print("in setup method")
print("executing " + method.__name__)
def teardown_method(self, method):
print(".....teardown")
if sys.exc_info()[0]:
test_method_name = method
print test_method_name
def test_failtest(self):
Assert.fail("failed test")
_
teardown_method()
失敗がない場合にのみ実行されます
あなたによると post stackoverflowで、私は私の頭の中にあることを共有できます、それが役立つことを願っています:ウィンク:あなたがしようとしているのは標準を処理することですAssertionErrorassertによって発生する可能性のある例外)キーワード、または nittest.TestCase に実装されているアサーションメソッド、またはカスタム例外を発生させるカスタムアサーションメソッド。これを行うには3つの方法があります。
try-except-finally構文を使用します。いくつかの基本的な例:
try: Assert.fail("failed test") except AssertionError: get_screenshot() raise
または、コンテキストマネージャーとしてwithステートメントを使用します。
class TestHandler: def __enter__(self): # maybe some set up is expected before assertion method call pass def __exit__(self, exc_type, exc_val, exc_tb): # catch whether exception was raised if isinstance(exc_val, AssertionError): get_screenshot() with TestHandler(): Assert.fail("failed test")
ここ あなたはそれで遊ぶ方法についてより深く掘り下げることができます
私の意見では、最後のアプローチは最もエレガントなアプローチです。 デコレータ を使用します。このデコレータを使用すると、任意のテスト方法を装飾できます。
def decorator_screenshot(func): def wrapper(*args, **kwargs): try: func(*args, **kwargs) except AssertionError: get_screenshot() raise return wrapper @decorator_screenshot def test_something(): Assert.fail("failed test")
いくつかの苦労の後、最終的にこれは私のために働いた。
Conftest.pyの場合:
@pytest.hookimpl(hookwrapper=True, tryfirst=True)
def pytest_runtest_makereport(item, call):
outcome = yield
rep = outcome.get_result()
setattr(item, "rep_" + rep.when, rep)
return rep
また、コードでは、フィクスチャ(テスト用のティアダウンフィクスチャなど)で次のように使用します。
def tear_down(request):
method_name = request.node.name
if request.node.rep_call.failed:
print('test {} failed :('.format(method_name))
# do more stuff like take a Selenium screenshot
「request」は、pytestがテストのコンテキストで提供するフィクスチャ「funcarg」であることに注意してください。自分で定義する必要はありません。
出典: pytestの例 および これを簡単にする(しない)スレッド 。
これが私たちのやり方です、注意__ multicall __ドキュメントが非常に少なく、読んだことを覚えています__ multicall __は非推奨になります。これを塩のピンチで使用し、置き換えてみてください__ multicall __ with 'item、call'例のとおり。
def pytest_runtest_makereport(__multicall__):
report = __multicall__.execute()
if report.when == 'call':
xfail = hasattr(report, 'wasxfail')
if (report.skipped and xfail) or (report.failed and not xfail):
try:
screenshot = APP_DRIVER.take_screen_shot(format="base64")
except Exception as e:
LOG.debug("Error saving screenshot !!")
LOG.debug(e)
return report
def pytest_runtest_makereport(item, call):
if call.when == 'call':
if call.excinfo is not None:
# if excinfor is not None, indicate that this test item is failed test case
error("Test Case: {}.{} Failed.".format(item.location[0], item.location[2]))
error("Error: \n{}".format(call.excinfo))