pycharm 返回方法的pytests fixture的类型提示

9wbgstp7  于 2023-10-20  发布在  PyCharm
关注(0)|答案(2)|浏览(149)

我的一些pytest fixture返回一个方法。我想对我所有的方法使用类型提示。要说一个方法返回一个方法,我可以在这里使用Callable。这里的问题是:我失去了IDE PyCharm中参数的自动完成功能。
不给fixture的返回值类型提示:

@pytest.fixture
def create_project():
    def create(location: Path, force: bool = True) -> bool:
        # ...

    return create

def test_project(create_project):
    project_created = create_project()

对于给定的类型提示:

@pytest.fixture
def create_project() -> Callable[[Path, bool], bool]:
    def create(location: Path, force: bool = True) -> bool:
        # ...

    return create

def test_project(create_project):
    project_created = create_project()

Callable的另一个问题是,我必须在fixture和使用该fixture的每个测试中描述一次参数和返回类型。
那么,有没有更有效的方法来做到这一点?

ogsagwnx

ogsagwnx1#

预期的方式似乎是使用协议:

from typing import Protocol

class ProjectMaker(Protocol):
    def __call__(self, location: Path, force: bool = True) -> bool: ...

@pytest.fixture
def create_project() -> ProjectMaker:
    def create(location: Path, force: bool = True) -> bool:
        ...

    return create

def test_project(create_project: ProjectMaker):
    project_created = create_project()

不幸的是,PyCharm(#PY-45438)目前不支持此功能。

lf5gs5x2

lf5gs5x22#

更具体地说,协议旨在实现duck-typing(例如,考虑“Iterable protocol”)。上述用法的问题是,any 对象实现了__call__,并具有所示的签名,将被视为ProjectMaker。(参见Carl Meyer's PyCon 2018 presentation示例)。
我相信一个可以接受的替代方案是使用TypeAlias来使你的类型提示更容易:

from pathlib import Path
from typing import TypeAlias

ProjectMaker: TypeAlias = Callable[[Path, bool], bool]

# Now use `ProjectMaker` throughout as before...

它也更短。请注意,您不必使用TypeAlias。它的存在纯粹是为了明确声明语句是类型别名,而不是普通的变量声明。(参见文档中的类型别名)

  • ASIDE:* 我用来确定是否使用Protocol的一个简短的经验法则是,我所说的是否是“-able”(Iterable,Callable,Reversible,Mutable,Mappable等)。如果是这样,我描述的是一个行为,Protocol是一个很好的选择。

相关问题