Mar*_*nen 8 python sqlalchemy python-3.x
游戏引擎为我提供了一个Player具有uniqueid只读属性的类来识别玩家.我想将其"转换"为SQLAlchemy,Column以便我可以像这样查询玩家:
query = session.query(Player).filter(Player.uniqueid=='STEAM_0:0:1234567')
player = query.one_or_none()
if player is None:
player = Player(uniqueid='STEAM_0:0:1234567')
Run Code Online (Sandbox Code Playgroud)
这是我班级目前的样子:
class Player(game.Player, db.Model):
_uniqueid = Column('uniqueid', String(21), unique=True, nullable=False)
def __init__(self, index, **kwargs):
game.Player.__init__(index) # initializes uniqueid
db.Model.__init__(_uniqueid=self.uniqueid, **kwargs)
Run Code Online (Sandbox Code Playgroud)
接下来我想为它创建一个只读接口_uniqueid,因此API用户不能再写入变量(好吧,他们可以通过_uniqueid,但这是他们的责任,因为访问它应该通过非私有uniqueid).
我想uniqueid用一个新原件覆盖原件:
@property
def uniqueid(self):
return self._uniqueid
Run Code Online (Sandbox Code Playgroud)
这是只读的并且"隐藏"原件_uniqueid,阻止任何人写入它,除非他们故意访问私有(我甚至不会在文档中列出它,我只会暴露非私有的).
唯一的问题是,这完全取代旧的,这意味着由于使用新的吸气剂而不是旧的吸气剂,我__init__的功能_uniqueid=self.uniqueid无法self.uniqueid使用.
总而言之,我想要的是将只读属性转换为可用于使用SQLAlchemy查询的只读属性.这是可能的,如果,如何?
您可以使用super来访问 的属性game.Player。我们可以使用 Cython 创建的简单 C 扩展类型进行测试:
# game.pyx
cdef class Player:
cdef int index;
def __init__(self, index):
self.index = index
@property
def uniqueid(self):
return "foo"
# test.py
class Player(game.Player, Base):
__tablename__ = "player"
id = Column(Integer, primary_key=True)
_uniqueid = Column('uniqueid', String(21), unique=True, nullable=False)
def __init__(self, index, **kwargs):
game.Player.__init__(self, index) # initializes uniqueid
Base.__init__(self, _uniqueid=super().uniqueid, **kwargs)
@property
def uniqueid(self):
return self._uniqueid
print(Player(1).uniqueid) # "foo"
Run Code Online (Sandbox Code Playgroud)
由于从 C 扩展类型继承的不确定性,这可能会也可能不会起作用,具体取决于类型game.Player使用的 C 魔法。
另外,由于 ORM__init__在从数据库加载实例时会绕过,因此您必须挂钩该load事件才能初始化game.Player类型。
| 归档时间: |
|
| 查看次数: |
254 次 |
| 最近记录: |