Skip to content

Instantly share code, notes, and snippets.

@tspng
Last active July 21, 2021 10:53
Show Gist options
  • Save tspng/36bcd79cc1233964d0205ffbda21363b to your computer and use it in GitHub Desktop.
Save tspng/36bcd79cc1233964d0205ffbda21363b to your computer and use it in GitHub Desktop.
SQLAlchemy custom query property problem
class _ForUserQuery(BaseQuery):
def _get_client_user_query(self):
raise NotImplementedError
def _get_pk_field(self):
raise NotImplementedError
def for_user(self, user):
query = self._get_client_user_query()
if not user.is_admin:
query = query.filter_by(user_id=user.id)
return query
def mine(self):
return self.for_user(current_user)
def get_mine_or_404(self, ident, description=None):
# TODO: check if there's a way to automatically get the pk field
# attribute that this query object is attached to
obj = self.mine().filter(self._get_pk_field() == ident).one_or_none()
if obj is None:
abort(404, description=description)
return obj
class _ClientsForUserQuery(_ForUserQuery):
def _get_client_user_query(self):
return self.join(ClientUser)
def _get_pk_field(self):
return Client.id
class _PagesForUserQuery(_ForUserQuery):
def _get_client_user_query(self):
return self.join(Client).join(ClientUser)
def _get_pk_field(self):
return Page.id
class ClientUser(db.Model):
user_id = db.Column(db.Integer, db.ForeignKey("user.id"), primary_key=True)
client_id = db.Column(db.Integer, db.ForeignKey("client.id"), primary_key=True)
client = db.relationship("Client", back_populates="users")
user = db.relationship("User", back_populates="clients")
class Client(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(255), unique=True, nullable=False)
users = db.relationship("ClientUser", back_populates="client")
pages = db.relationship("Page", back_populates="client")
query_class = _ClientsForUserQuery
class Page(db.Model):
id = db.Column(db.Integer, primary_key=True)
title = db.Column(db.String(255), nullable=False)
client_id = db.Column(db.Integer, db.ForeignKey("client.id"))
client = db.relationship("Client", back_populates="pages")
query_class = _PagesForUserQuery
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment