【发布时间】:2022-10-06 09:13:07
【问题描述】:
我有一个这样的模型:
class User:
__tablename__ = \"user\"
first_name = Column(String(), nullable=False)
last_name = Column(String(), nullable=False)
然后我有一个这样的查询:
name = [\"...\", ...]
user_query = (
db.session.query(User)
.add_column(case([
(and_(User.first_name).ilike(f\'%{name}%\'), User.last_name.ilike(f\'%{name}%\')), True),
(or_(User.first_name).ilike(f\'%{name}%\'), User.last_name.ilike(f\'%{name}%\')), False)
]).label(\'perfect_match\'))
.order_by(literal_column(\"\'perfect_match\"))
)
这显然是一种过度简化,但基本上我正在尝试跨字段进行搜索并将完美匹配与不完美匹配分开排序。
这给了我一个错误,说“完美匹配”列不存在,所以我认为我在这里错误地使用了add_column。
我也尝试像这样使用hybrid_method:
@hybrid_method
def perfect_match(self, terms):
perfect_match = True
matched = False
for term in terms:
if term.lower() in self.first_name.lower() or term.lower() in self.last_name.lower():
matched = True
continue
perfect_match = False
return perfect_match if matched else None
@perfect_match.expression
def perfect_match(self, terms):
perfect_match = and_(...)
imperfect_match = or_(...)
return case(...)
然后我的查询如下所示:
name = [...]
user_query = (
db.session.query(User)
.filter(User.perfect_match(name) != None)
.order_by(User.perfect_match(name))
我希望perfect_match 在输出中。这是我想要的 SQL:
SELECT
first_name,
last_name,
case (
...
) as perfect_match
FROM user
WHERE perfect_match != NULL
ORDER BY perfect_match
第一次使用add_column 给了我那个SQL,但是SQLAlchemy 错误说它不能列perfect_match 不存在。第二个(使用hybrid_method)将 case 放在 WHERE 和 ORDER BY 子句中(可能效率低下?)并且在输出中不包括 perfect_match,但它似乎工作正常。我需要使用该输出列来确定完美匹配的结束位置。
我试过了:
- 将完美匹配添加为列(布尔值)
- 将完美匹配添加为 column_property()
- 将 perfect_match 添加为 .query(User, literal_column(\"\'perfect_match\"))
有什么想法吗?我见过的大多数例子都使用hybrid_property,但我需要在这里提出一个论点。我对 SQLAlchemy 很陌生,所以我可能错过了一些东西。
标签: python postgresql sqlalchemy