SqlAlchemy:获取可以包含多种类型对象的关系中特定类型的实例

发布于 2024-11-07 13:19:01 字数 2664 浏览 2 评论 0原文

我有一个带有“BaseVisibilizer”类的应用程序,该类是基础类 其他两个类的类:

class BaseVisibilizer(declarativeBase):
       __tablename__ = "base_visibilizers"
       _polymorphicIdentity = Column("polymorphic_identity", String(20), key="polymorphicIdentity")
       __mapper_args__ = {
               'polymorphic_on': _polymorphicIdentity,
               'polymorphic_identity': None
       }

       def __init__(self):
               super(BaseVisibilizer, self).__init__()

这是我的 User 和 UserGroup 类的基类:这两个类 可用于控制某些项目的可见性。

class UserGroup(BaseVisibilizer.BaseVisibilizer):
       __tablename__ = "user_groups"
       _id = Column("id", Integer, ForeignKey(BaseVisibilizer.BaseVisibilizer.id), primary_key=True)

       __mapper_args__ = {
               'polymorphic_identity': 'UserGroup',
               'inherit_condition': _id == BaseVisibilizer.BaseVisibilizer._id,
       }

       _name = Column("name", String(50), nullable=False)

class User(BaseVisibilizer.BaseVisibilizer):
       __tablename__ = "users"
       _id = Column("id", Integer, ForeignKey(BaseVisibilizer.BaseVisibilizer.id), primary_key=True)

       __mapper_args__ = {
               'polymorphic_identity': 'User',
               'inherit_condition': _id == BaseVisibilizer.BaseVisibilizer._id,
       }
       _firstName = Column("first_name", String(50), key="fistName")
       _lastName = Column("last_name", String(50), key="lastName")
       _userName = Column("user_name", String(50), unique=True, nullable=False)

在我的系统的许多其他类中,我有这样的关系: 可以包含“BaseVisibilizers”(用户或用户组)。

class Whatever(declarativeBase):
       allowedVisibilizers = relationship("BaseVisibilizer",
               secondary="intermediate_whatevers_to_base_visibilizers",
               collection_class=set)

因此,在 Whatever 的实例中,allowedVisibilizers 集可以 包含 User 或 UserGroup 的实例(因为两者都是 基础可视化器)。如果登录用户或登录用户的用户组 属于“allowedVisibilizers”,该用户将能够 访问(或“查看”)Whatever 的实例。

在某个时刻,我想在“Whatever”中创建一个方法 类只会给我允许的可见性 实际上是一个用户组(丢弃用户),但我无法 做吧。

我尝试了几件事,但显然不是正确的 (子查询、“allowedvisibilizers”的连接...):(

What I'd like is something like:
class Whatever(declarativeBase):
       [ . . . ]
       def getAllowedUserGroups(self):
               session = Database.Session()
               query = session.query(UserGroup.UserGroup).filter(UserGroup.UserGroup.in_(self.allowedVisibilizers))
               return query.all()

但显然,UserGroup 是一个类并且没有 in_)

当然,我总是可以获取所有“allowedVisibilizers”并删除 来自返回值的用户,但我试图使其成为 比这稍微优化一下,避免不必要的调用 数据库。

任何提示将不胜感激。先感谢您!

I have an application with a "BaseVisibilizer" class that is base
class for two other classes:

class BaseVisibilizer(declarativeBase):
       __tablename__ = "base_visibilizers"
       _polymorphicIdentity = Column("polymorphic_identity", String(20), key="polymorphicIdentity")
       __mapper_args__ = {
               'polymorphic_on': _polymorphicIdentity,
               'polymorphic_identity': None
       }

       def __init__(self):
               super(BaseVisibilizer, self).__init__()

This is the base class for my User and UserGroup classes: both classes
can be used to control the visibility of certain items.

class UserGroup(BaseVisibilizer.BaseVisibilizer):
       __tablename__ = "user_groups"
       _id = Column("id", Integer, ForeignKey(BaseVisibilizer.BaseVisibilizer.id), primary_key=True)

       __mapper_args__ = {
               'polymorphic_identity': 'UserGroup',
               'inherit_condition': _id == BaseVisibilizer.BaseVisibilizer._id,
       }

       _name = Column("name", String(50), nullable=False)

class User(BaseVisibilizer.BaseVisibilizer):
       __tablename__ = "users"
       _id = Column("id", Integer, ForeignKey(BaseVisibilizer.BaseVisibilizer.id), primary_key=True)

       __mapper_args__ = {
               'polymorphic_identity': 'User',
               'inherit_condition': _id == BaseVisibilizer.BaseVisibilizer._id,
       }
       _firstName = Column("first_name", String(50), key="fistName")
       _lastName = Column("last_name", String(50), key="lastName")
       _userName = Column("user_name", String(50), unique=True, nullable=False)

In many of the other classes of my system I have a relationship that
can contain "BaseVisibilizers" (Users or UserGroups).

class Whatever(declarativeBase):
       allowedVisibilizers = relationship("BaseVisibilizer",
               secondary="intermediate_whatevers_to_base_visibilizers",
               collection_class=set)

So in the instances of Whatever, the allowedVisibilizers set can
contain instances of User of UserGroup (because both are
BaseVisibilizers). If the logged user or the UserGroup the logged user
belongs to is among the "allowedVisibilizers" , that user will be able
to access (or "see") that instance of Whatever.

At a certain point, I would like to create a method in the Whatever
class that would give me only the allowed visibilizers that are
actually a UserGroup (discarding the Users) but I haven't been able to
do it.

I've tried several things, but obviously, not the right one
(subqueries, joins of "allowedvisibilizers"...):

What I'd like is something like:
class Whatever(declarativeBase):
       [ . . . ]
       def getAllowedUserGroups(self):
               session = Database.Session()
               query = session.query(UserGroup.UserGroup).filter(UserGroup.UserGroup.in_(self.allowedVisibilizers))
               return query.all()

(but obviously, UserGroup is a class and doesn't have an in_)

Of course, I could always get all the "allowedVisibilizers" and remove
the Users from the returned value, but I was trying to make it a
little bit optimized than that and avoid unnecessary calls to the
database.

Any hint will be very appreciated. Thank you in advance!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

我一直都在从未离去 2024-11-14 13:19:01

一种解决方案是在 Whatever 上创建另一个关系,其中包含特定表 UserGroup 的过滤器,这应该可以解决问题。
请参阅针对相同的父/子文档以获取更多信息。在您的情况下,在 UserGroup 表上添加额外的联接条件应该可以解决问题。
另请考虑使用
构建启用查询的属性 指定只读

One solution would be to create another relationship on Whatever which would include the filter to the specific table UserGroup, which should do the trick.
See Multiple Relationships against the Same Parent/Child documentation for more information. In your case adding additional join condition on UserGroup table should do the trick.
Also consider using Building Query-Enabled Properties to specify readonly.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文