You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在自定义__setattr__方法后让coc-pyright正常报告reportAttributeAccessIssue问题

如何在自定义__setattr__方法后让coc-pyright正常报告reportAttributeAccessIssue问题

这个问题其实是因为当你自定义__setattr__方法时,pyright会默认认为你希望处理所有属性的赋值操作(包括未预先定义的属性),所以自动关闭了未知属性的访问检查。要同时保留自定义__setattr__和静态检查功能,你可以试试下面几种方案:

方案一:使用__slots__限制允许的属性

如果你的类不需要动态添加属性,直接用__slots__明确列出所有允许的属性。这样即使你自定义了__setattr__,pyright也会严格检查赋值的属性是否在__slots__列表中:

from pydantic import BaseModel

class User2(BaseModel):
    __slots__ = ("name", "age")
    name: str
    age: int

    def __setattr__(self, key, value):
        super().__setattr__(key, value)

user2 = User2(name="Alice", age=1)
user2.foo = 1  # coc-pyright会正常报错:Cannot assign to attribute "foo" for class "User2"

方案二:给__setattr__的key参数添加精确的类型注解

通过Literal类型明确指定__setattr__接受的属性名,这样pyright会在静态检查时验证传入的key是否符合要求:

from pydantic import BaseModel
from typing import Literal

class User2(BaseModel):
    name: str
    age: int

    def __setattr__(self, key: Literal["name", "age"], value):
        super().__setattr__(key, value)

user2 = User2(name="Alice", age=1)
user2.foo = 1  # coc-pyright会报错:Argument of type "Literal['foo']" cannot be assigned to parameter "key" of type "Literal['name', 'age']"

这种方式适合属性数量不多的类,如果属性较多,你可以借助typing.get_type_hints来动态生成允许的属性名类型,不过写法会稍微复杂一点。

方案三:结合运行时检查和静态提示

如果你需要更灵活的处理,可以在自定义__setattr__中手动检查属性是否属于模型的预定义字段,同时通过类型注解辅助pyright识别:

from pydantic import BaseModel
from typing import Literal

class User2(BaseModel):
    name: str
    age: int

    # 动态生成允许的属性名类型
    _allowed_attrs = Literal[tuple(model_fields.keys())]

    def __setattr__(self, key: _allowed_attrs, value):
        # 运行时额外验证,防止绕过静态检查的情况
        if key not in self.model_fields:
            raise ValueError(f"未知属性:{key}")
        super().__setattr__(key, value)

user2 = User2(name="Alice", age=1)
user2.foo = 1  # coc-pyright会报错,同时运行时也会抛出异常

这样既保留了自定义__setattr__的逻辑,又能让pyright正常进行未知属性的检查,还能在运行时提供额外的保障。

备注:内容来源于stack exchange,提问作者user2976130

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.13 19:49:28