本文介绍了如何让 pytest 等待(手动)用户操作?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们成功地使用 pytest (Python 3) 运行测试套件来测试一些硬件设备(电子产品).对于这些测试的一个子集,我们需要测试人员更改硬件布置,然后再将其更改回来.我的方法是使用附加到相关测试的模块级夹具(它们都在一个单独的模块中),并带有两个 input 调用:

@pytest.fixture(scope="module")def disconnect_component():input('断开组件,然后按回车')yield # 此时所有使用这个fixture的测试都运行了input('再次连接组件,然后按回车')

运行时,我得到OSError:在捕获输出时从标准输入读取.我可以通过使用 --capture=no 调用 pytest 来避免这种情况,并且已经确认我的方法有效,这意味着我在有问题的测试子集之前获得第一个查询,而在它们运行之后获得第二个查询.

最大的缺点是这会停用整个测试套件的 stdin/stderr 捕获,而其他一些测试依赖于此.

我也尝试使用 capsys.disabled (docs) 像这样

@pytest.fixture(scope="module")def disconnect_component(capsys):使用 capsys.disabled():input('断开组件,然后按回车')yield # 此时所有使用这个fixture的测试都运行了input('再次连接组件,然后按回车')

但是在运行它时,我得到 ScopeMismatch:您尝试使用模块"范围的请求对象访问功能"范围的装置capsys",涉及工厂.

我可以让 pytest 以 input 以外的其他方式等待用户操作吗?如果没有,我是否可以仅针对使用上述夹具的测试禁用捕获?

解决方案

于是,我找到了一个 提示 由 pytest 开发人员提供,基于此我基本上做了 capsys.disable() 函数所做的:

@pytest.fixture(scope="module")def disconnect_component(pytestconfig):capmanager = pytestconfig.pluginmanager.getplugin('capturemanager')capmanager.suspend_global_capture(in_=True)input('断开组件,然后按回车')capmanager.resume_global_capture()yield # 此时所有使用这个fixture的测试都运行了capmanager.suspend_global_capture(in_=True)input('再次连接组件,然后按回车')capmanager.resume_global_capture()

就我所见,这完美无缺.不要忘记 in_=True 位.

从 pytest 3.3.0(我认为),capmanager.suspendcapturecapmanager.resumecapture重命名capmanager.suspend_global_capturecapmanager.

We are sucessfully using pytest (Python 3) to run a test suite testing some hardware devices (electronics). For a subset of these tests, we need the tester to change the hardware arrangement, and afterwards change it back. My approach was to use a module-level fixture attached to the tests in question (which are all in a separate module), with two input calls:

@pytest.fixture(scope="module")
def disconnect_component():
    input('Disconnect component, then press enter')
    yield  # At this point all the tests with this fixture are run
    input('Connect component again, then press enter')

When running this, I get OSError: reading from stdin while output is captured. I can avoid this by calling pytest with --capture=no, and have confirmed that my approach works, meaning I get the first query before the test subset in question, and the second one after they have run.

The big drawback is that this deactivates capturing stdin/stderr for the whole test suite, which some of the other test rely on.

I also tried to use capsys.disabled (docs) like this

@pytest.fixture(scope="module")
def disconnect_component(capsys):
    with capsys.disabled():
        input('Disconnect component, then press enter')
        yield  # At this point all the tests with this fixture are run
        input('Connect component again, then press enter')

but when running this I get ScopeMismatch: You tried to access the 'function' scoped fixture 'capsys' with a 'module' scoped request object, involved factories.

Can I make pytest wait for user action in some other way than input? If not, can I disable capturing just for the tests using above fixture?

解决方案

So, I found a hint by a pytest dev, based on which I basically do what the capsys.disable() function does:

@pytest.fixture(scope="module")
def disconnect_component(pytestconfig):
    capmanager = pytestconfig.pluginmanager.getplugin('capturemanager')

    capmanager.suspend_global_capture(in_=True)
    input('Disconnect component, then press enter')
    capmanager.resume_global_capture()

    yield  # At this point all the tests with this fixture are run

    capmanager.suspend_global_capture(in_=True)
    input('Connect component again, then press enter')
    capmanager.resume_global_capture()

This works flawlessly as far as I can see. Don't forget the in_=True bit.

Edit: From pytest 3.3.0 (I think), capmanager.suspendcapture and capmanager.resumecapture were renamed to capmanager.suspend_global_capture and capmanager.resume_global_capture, respectively.

这篇关于如何让 pytest 等待(手动)用户操作?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-15 03:23