mypy spurious error:" module"没有属性" XPath"与etree

时间:2016-09-08 05:04:31

标签: python lxml mypy

我尝试使用mypy在一些使用LXML库来解析XML的代码中进行类型检查。

在我使用etree.XPath的每一行上,我从mypy收到虚假错误。例如,以下琐碎的脚本

from lxml import etree    
NameXPath = etree.XPath("Name/text()")

生成错误

test.py:3: error: "module" has no attribute "XPath"

但脚本运行正常,我的XPath在运行时正常工作。

我还尝试了#type:ignore导入,我认为mypy可能会告诉from lxml import etree # type:ignore NameXPath = etree.XPath("Name/text()") 不要键入 - 检查该库,但这并没有抑制错误。

etree.XPath

通过将etree.XPath的调用转移到一个没有任何类型注释的单独函数中,我确实取得了一些成功,但这看起来像是一个黑客,迫使我安排我的代码笨拙。

我想知道是否有办法完全抑制这些虚假错误,或者可能暗示mypy函数确实存在,因为它似乎无法解决这个问题独自出来。

要明确的是,我并不关心lxml知道etree.XPath库中出现的结构的正确类型。我更关心的是将类型信息放在我自己的类上,我将解析后的信息推入,所以我想要使用mypy进行查询的类型检查函数,找到数据,然后将它们推送到我的脚本中定义的类型注释类。

etree似乎无法解决etree.parse中的其他功能,例如我对mypy的调用很好

我目前正在使用indexOf 0.4.4

1 个答案:

答案 0 :(得分:4)

看起来这是typeshed中的一个错误,这是stdlib和各种第三方库的社区贡献的类型注释集合。

特别是,看起来stubs for lxml完全缺少XPath的定义。这可能是疏忽 - 我会尝试在问题跟踪器上提交错误或尝试提交包含修复的拉取请求。

修复后,mypy会使用最新版本的typeshed重新启动,你需要暂时从git repo安装mypy(至少,直到mypy 0.4.5出现在某个时间) 10月)。

与此同时,您可以通过以下方式解决此问题:

from lxml.etree import XPath  # type: ignore
NameXPath = XPath("Name/text()")
# mypy considers NameXPath to have a type of Any

...或者,如果您希望更具体地定义XPath,请执行以下操作:

import typing

if typing.TYPE_CHECKING:
    # typing.TYPE_CHECKING is always False at runtime, so this
    # branch is parsed by typecheckers only
    class XPath:
        # Provide a method header stubs with signatures to fool
        # mypy into understanding what the interface for XPath is
else:
    # Actually executed at runtime
    from lxml.etree import XPath  # type: ignore

NameXPath = XPath("Name/text()")