2024年06月18日 SQLAlchemy hybrid property 极客笔记
在使用SQLAlchemy进行数据库操作时,有时候我们需要在模型中添加一些计算属性,通常我们可以采用@property
装饰器来实现。但是如果我们需要在查询时使用这些计算属性,@property
就无法满足我们的需求了。这时,hybrid_property
就可以发挥作用了。
hybrid_property
是SQLAlchemy提供的一个装饰器,可以将一个Python属性转换为SQLAlchemy的混合属性,使得该属性既可以在Python代码中使用,也可以在SQL查询中使用。
首先,我们需要导入hybrid_property
:
from sqlalchemy.ext.hybrid import hybrid_property
然后,我们可以在一个SQLAlchemy的模型中定义一个hybrid_property
,示例如下:
from sqlalchemy.ext.hybrid import hybrid_property
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy import create_engine, Column, Integer, String
Base = declarative_base()
class User(Base):
__tablename__ = 'users'
id = Column(Integer, primary_key=True)
first_name = Column(String)
last_name = Column(String)
@hybrid_property
def full_name(self):
return f"{self.first_name} {self.last_name}"
@full_name.expression
def full_name(cls):
return cls.first_name + " " + cls.last_name
在上面的示例中,我们在User
模型中定义了一个full_name
的hybrid_property
。在Python代码中,我们可以通过user.full_name
得到用户的全名;在SQL查询中,我们也可以通过User.full_name
来访问这个属性。
下面我们来看看如何在SQL查询中使用hybrid_property
:
from sqlalchemy.orm import sessionmaker
engine = create_engine('sqlite:///:memory:')
Base.metadata.create_all(engine)
Session = sessionmaker(bind=engine)
session = Session()
user1 = User(first_name='John', last_name='Doe')
session.add(user1)
session.commit()
# 测试在Python代码中使用hybrid_property
print(user1.full_name) # Output: John Doe
# 测试在SQL查询中使用hybrid_property
user_full_names = session.query(User.full_name).all()
for full_name in user_full_names:
print(full_name) # Output: ('John Doe',)
在上面的示例中,我们在数据库中插入了一个用户,并获取了该用户的全名。可以看到,不仅可以在Python代码中使用full_name
属性,还可以在SQL查询中获取full_name
属性的值。
hybrid_property
必须要有一个对应的Python实现(即@hybrid_property
装饰器下的函数),这个Python实现的作用是在Python代码中计算属性的值。hybrid_property
还需要有一个对应的表达式实现(即@property_name.expression
装饰器下的函数),这个表达式实现的作用是在SQL查询中计算属性的值。本文链接:http://so.lmcjl.com/news/6821/