python - How to filter a Model with a One-To-Many Relationship using Flask-Sqlalchemy?
问题描述
I'm new to Flask-SQL-Alchemy so this may be a noob quesiton. Let's say I have a Tweet model:
class Tweet(db.Model):
__tablename__ = 'tweet'
id = db.Column(db.Integer, primary_key=True)
text = db.Column(db.String(500), nullable=False)
user_id = db.Column(db.Integer, db.ForeignKey('user.id'), nullable=False)
And a User model, which can have many tweets:
class User(db.Model):
__tablename__ = 'user'
id = db.Column(db.Integer, primary_key=True)
first_name = db.Column(db.String(50), nullable=False)
last_name = db.Column(db.String(50), nullable=False)
birth_year = db.Column(db.Integer)
tweets = db.relationship('Tweet', backref='user', lazy=True)
Now, I want to apply different filters on the User table. For example, to fetch all the users born in 1970
whose first name is John
filters = (
User.first_name == 'John',
User.birth_year == 1970
)
users = User.query.filter(*filters).all()
So far, so good! But now I want to add a filter for the tweets
attribute which notice is not a real database column but rather something provided by the ORM. How can I fetch John
s who have posted more than 20 tweets? I tried:
filters = (
User.first_name == 'John',
len(User.tweets) > 20
)
But this raises an Exception: object of type 'InstrumentedAttribute' has no len()
.
I have also tried adding a new hybrid property in the User model:
class User(db.Model):
...
@hybrid_property
def tweet_count(self):
return len(self.tweets)
filters = (
User.first_name == 'John',
User.tweet_count > 20
)
But I still get the same error. This seems like a common task but I'm not able to find any documentation or related examples. Am I approaching the problem the wrong way?
解决方案
I think you are missing the second part as seen here SQLAlchemy - Writing a hybrid method for child count
from sqlalchemy.sql import select, func
class User(db.Model):
#...
@tweet_count.expression
def tweet_count(cls):
return (select([func.count(Tweet.id)]).
where(Tweet.user_id == cls.id).
label("tweet_count")
)
推荐阅读
- javascript - 如何在 html 中从本地 JSON 中搜索项目名称/ID?
- jquery - jQuery自动完成冻结了最初的几个字母
- wordpress - 使用帖子名永久链接时,具有不同站点 url 的 Wordpress 会导致主页重定向循环
- arrays - 什么时候用方括号,什么时候用圆括号?
- php - 在 wordpress 和 woocommerce 上为菜单项设置唯一类
- java - 打印每个请求的请求 ID
- opencv - 如何在 OpenCV cv::cuda::GpuMat 或 cv::ogl::Buffer 图像对象上绘制文本和矩形?
- parsley.js - 如何使用 parsley.js 验证整个表单
- django-queryset - Django Queryset 将每个用户与组结合起来?
- php - AJAX图片上传FormData问题