首页 > 解决方案 > 如何覆盖 pytest 中注入测试函数参数的函数?

问题描述

我正在使用snapshottest 包添加使用快照进行测试的可能性。这为我们的测试增加了很多价值和速度。

这是这样工作的:

def test_my_fn(foo, bar, snapshot):
    snapshot.assert_match(my_fn(foo, bar))

第一次测试运行时,snapshot 会保存 的输出,my_fn(foo, bar)然后,每次测试运行时,它都会检查my_fn(foo, bar)保存的快照的输出。

但是,我对snapshot.assert_match保存对象的方式有疑问。我正在使用匀称的几何图形,并且快照不会立即将匀称的对象写入。它保存为<shapely.geometry.polygon.Polygon object at 0x1000000>在其他情况下导致测试失败的原因。

所以我写了一个函数dump_geometry,将几何转换成字典,然后,snapshot.assert_match可以正确地写快照。

我通过以下方式使其工作:

def test_my_fn(foo, bar, snapshot):
    snapshot.assert_match(dump_geometry(my_fn(foo, bar)))

这很好用,但我必须将它添加到我拥有的每个测试中。我想知道是否有办法覆盖snapshot.assert_match第一次调用dump_geometry,然后使用原始的snapshot.assert_match.

我不知道如何做到这一点。我尝试使用固定装置,但没有进展。

哦,我可能会补充一点,我希望这是snapshot.assert_match. 我的意思是,要全球化。


编辑 1:根据@BorrajaX 评论,我将添加更多信息:

我不仅有 my_fn,而且还有数百个函数可以填充这个场景。我还使用mark.parametrizediff 输入运行相同的测试:

@mark.parametrize('foo, bar', [(1,2), (2, 3), (4, 5)])
def test_my_fn(foo, bar, snapshot):
    snapshot.assert_match(dump_geometry(my_fn(foo, bar)))


@mark.parametrize('foo, bar, baz', [
   ('a',shapely.geometry.Polygon(), [1,2.3]),
   ('b',shapely.geometry.MultiPolygon(), [1.7,2,6]), 
   ('c',shapely.geometry.LineString(), [])])
def test_my_fn2(foo, bar, baz, snapshot):
    snapshot.assert_match(dump_geometry(my_fn2(foo, bar, baz)))


@mark.parametrize('foo', [
   (shapely.geometry.MultiLineString()), 
   (shapely.geometry.LineString()), 
   (shapely.geometry.Polygon()), ])
def test_my_fn3(foo, bar, snapshot):
    snapshot.assert_match(dump_geometry(my_fn3(foo, bar)))

我想避免snapshot.assert_match(dump_geometry(...))在每次测试时都写,当被dump_geometry调用时会自动调用snapshot.assert_match,无论是通过覆盖它还是以其他方式。

标签: pythonpytest

解决方案


推荐阅读