Mypy 捕获 AttributeError

Mypy catch AttributeError

一直在使用以下代码

import yaml
try:
    filterwarnings(yaml.YAMLLoadWarning)
except AttributeError:
    pass

但是当我今天尝试 运行 mypy 时,我得到了 "module has no attribute YAMLLoadWarning"。这在 python 的某些版本上是正确的。有没有更好的写法?

编辑:

更清楚一点,我知道如何忽略错误(并捕获与 python 3.6 版本的 pyyaml 相关的异常,不包括该异常)。我的问题更多是关于使用解析器的。考虑这些例子-

我知道如果你有一个函数 returns 更具体的类型

def bad(a: Optional[int]) -> int:
    return a  # Incompatible return value type (got "Optional[int]", expected "int")

您可以使用分支强制只返回正确的类型,解析器会注意到

def good(a: Optional[int]) -> int:
    if a:
        return a
    return 0

因此,在您使用 try/catch 语句处理错误情况的情况下,有没有一种方法可以构造它以便解析器意识到属性错误已被处理?

def exception_branch(a: Optional[str])-> list:
    try:
        return a.split()  # Item "None" of "Optional[str]" has no attribute "split"
    except:
        return []

我假设您使用的是 PyYAML?

在这种情况下,最好的 long-term 解决方法可能是您向 Typeshed 提交拉取请求,包括此 class 的类型提示。 (Typeshed 是标准库模块和 select 第三方模块的类型提示的存储库。PyYAML happen to be included within typeshed here 的存根。)

PyYAML 似乎在模块的 __init__.py file so you should probably add type hints for that class within the corresponding __init__.pyi file in Typeshed.

中定义了 YAMLLoadWarning

然后等待 mypy 的下一个版本——它在发布时包含最新可用版本的 Typeshed。

我相信 mypy 实际上已计划发布 later today,因此如果您最终提交 PR,时间可能会有点紧。但最坏的情况是,您只需要再等一两个月才能发布后续的 mypy。

同时,您可以在该行添加 # type: ignore 注释,如 .

如果你这样做,我还推荐 运行 带有 --warn-unused-ignores 命令行标志的 mypy。随着时间的推移,这将帮助您找到 # type: ignore 不再需要的评论作为 mypy releases/improves。

So in situations where you handle error situations using a try/catch statement, is there a way to construct this so that the parser realizes that the attribute error is handled?

不,恐怕没有。问题是 catch AttributeError 没有指出异常来自哪里。所以如果你有

try:
    print(foo.barr)
    return a.split()
except AttributeError:
    return []

类型检查器可以忽略 a 可以是 None 的事实,但它也必须忽略您拼错 bar 并且没有 barr 的事实] 对象中的属性 foo。另见 here