抽象类和 PyMongo;无法实例化抽象类 [英] Abstract classes and PyMongo; can't instantiate abstract class
问题描述
我创建了空抽象类 AbstractStorage
并从它继承了 Storage
类:
导入 abc将 pymongo 导入为 mongo主机 = mongo.MongoClient()打印(host.alive()) # 真类抽象存储(元类= abc.ABCMeta):经过类存储(抽象存储):dbh = 主机def __init__(self):打印('__init__')贮存()
我希望输出是
真__在里面__
然而,我得到的是
真回溯(最近一次调用最后一次): 中的文件/home/vaultah/run.py",第 16 行贮存()类型错误:无法使用抽象方法 dbh 实例化抽象类 Storage
如果我删除 metaclass=abc.ABCMeta
(以便 AbstractStorage
成为普通类)和/或如果我设置 ,问题(显然)就会消失dbh
为其他值.
这是怎么回事?
这真的不是 ABC 的问题,而是 PyMongo 的问题.此处存在一个问题.pymongo 似乎覆盖了 __getattr__
以返回某种数据库类.这意味着 host.__isabstractmethod__
返回一个 Database 对象,这在布尔上下文中为真.这导致 ABCMeta 认为 host
是一个抽象方法:
问题报告中描述的解决方法是在您的对象上手动设置 host.__isabstractmethod__ = False
.关于该问题的最后一条评论表明已针对 pymongo 3.0 进行了修复.
I created the empty abstract class AbstractStorage
and inherited the Storage
class from it:
import abc
import pymongo as mongo
host = mongo.MongoClient()
print(host.alive()) # True
class AbstractStorage(metaclass=abc.ABCMeta):
pass
class Storage(AbstractStorage):
dbh = host
def __init__(self):
print('__init__')
Storage()
I expected the output to be
True
__init__
however, the one I'm getting is
True
Traceback (most recent call last):
File "/home/vaultah/run.py", line 16, in <module>
Storage()
TypeError: Can't instantiate abstract class Storage with abstract methods dbh
The problem (apparently) goes away if I remove metaclass=abc.ABCMeta
(so that AbstractStorage
becomes an ordinary class) and/or if I set dbh
to some other value.
What's going on here?
This isn't really a problem with ABCs, it's a problem with PyMongo. There is an issue about it here. It seems that pymongo overrides __getattr__
to return some sort of database class. This means that host.__isabstractmethod__
returns a Database object, which is true in a boolean context. This cause ABCMeta to believe that host
is an abstract method:
>>> bool(host.__isabstractmethod__)
True
The workaround described in the issue report is to manually set host.__isabstractmethod__ = False
on your object. The last comment on the issue suggests a fix has been put in for pymongo 3.0.
这篇关于抽象类和 PyMongo;无法实例化抽象类的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!