【问题标题】:pytest: monkeypatch while using hypothesispytest:使用假设时的monkeypatch
【发布时间】:2020-12-28 18:35:01
【问题描述】:

在单元测试中,我使用monkeypatch 来更改dict 中的条目。

from hypothesis import given, strategies
    
    
test_dict = {"first": "text1", "second": "text2"}
    
    
given(val=strategies.text())
def test_monkeypath(monkeypatch, val):
    monkeypatch.setitem(test_dict, "second", val)
    
    assert isinstance(test_dict["second"], str)

测试通过,但在使用pytest 执行以下测试代码时收到警告。

=================================================================================================================== warnings summary ====================================================================================================================
.PyCharm2019.2/config/scratches/hypothesis_monkeypatch.py::test_monkeypath
  c:\users\d292498\appdata\local\conda\conda\envs\pybt\lib\site-packages\hypothesis\extra\pytestplugin.py:172: HypothesisDeprecationWarning: .PyCharm2019.2/config/scratches/hypothesis_monkeypatch.py::test_monkeypath uses the 'monkeypatch' fixture, wh
ich is reset between function calls but not between test cases generated by `@given(...)`.  You can change it to a module- or session-scoped fixture if it is safe to reuse; if not we recommend using a context manager inside your test function.  See h
ttps://docs.pytest.org/en/latest/fixture.html#sharing-test-data for details on fixture scope.
    note_deprecation(

-- Docs: https://docs.pytest.org/en/stable/warnings.html
============================================================================================================= 1 passed, 1 warning in 0.30s ==============================================================================================================

这是否意味着无论hypothesis生成多少个测试用例,dict的值都只会改变一次?
在这种情况下,我不确定如何使用上下文管理器。有人可以指出我正确的方向吗?

【问题讨论】:

    标签: pytest monkeypatching hypothesis-test python-hypothesis


    【解决方案1】:

    您的问题是 dict 仅针对所有测试调用修补一次,Hypothesis 正在警告您。如果您在monkeypatch.setitem 行之前有任何逻辑,那就太糟糕了!

    您可以通过using monkeypatch directly 解决此问题,而不是通过夹具:

    from hypothesis import given, strategies
    from _pytest.monkeypatch import MonkeyPatch
    
    
    test_dict = {"first": "text1", "second": "text2"}
    
    
    @given(val=strategies.text())
    def test_monkeypath(val):
        assert test_dict["second"] == "text2"  # this would fail in your version
    
        with MonkeyPatch().context() as mp:
            mp.setitem(test_dict, "second", val)
            assert test_dict["second"] == val
    
        assert test_dict["second"] == "text2"
    

    ,没有警告。

    【讨论】:

    • 您的确切代码在我的机器上不起作用。我确实在第 12 行收到了AttributeError: __enter__。您能验证一下吗?
    • 错别字,抱歉 - 应该是 with MonkeyPatch().context() as mp:
    【解决方案2】:

    使用monkeypatch context manager

    @given(val=strategies.text())
    def test_monkeypath(monkeypatch, val):
        with monkeypatch.context() as m:
            m.setitem(test_dict, "second", val)
    
            assert isinstance(test_dict["second"], str)
    

    【讨论】:

    • 代码正在运行,但是警告并没有消失。这是为什么?我可以确定忽略此警告吗?
    猜你喜欢
    • 2017-11-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-11-18
    • 1970-01-01
    • 1970-01-01
    • 2022-01-02
    • 1970-01-01
    相关资源
    最近更新 更多