fix(groups): 字节序排序按方言——MySQL CAST AS BINARY / SQLite COLLATE BINARY

collate("BINARY") 被 SQLAlchemy 反引号成标识符致 MySQL 500;SQLite 的
CAST AS BINARY 语义不符(排序键失效退化 room_id 序,测试失去判别力)。
按 session.bind.dialect 分支,两库都用真字节序。

726 测试绿。

Co-Authored-By: Claude Code <noreply@anthropic.com>
This commit is contained in:
浅念
2026-09-10 14:37:07 +08:00
parent acd6997bf0
commit 80b721b84f
+12 -3
View File
@@ -104,11 +104,20 @@ async def list_groups(
if (channel or "wechat") == "wechat":
# 云客「微信群统计」同款排序(2026-09-10 真机终判):owner_account_id
# (=微信号/wxid 混存,如 Nancyjade < csf7169708 < wxid_01gv…——大写
# 在小写前=区分大小写)**二进制字符串升序**分组,组内 room_id 字符串
# 升序。COLLATE BINARY 双库通用(MySQL/SQLite)。WA 保持最近活跃优先。
# 在小写前=区分大小写)**二进制字节序升序**分组,组内 room_id 字符串
# 升序。字节序按方言:MySQL 用 CAST(col AS BINARY)(collate("BINARY")
# 会被 SQLAlchemy 反引号成标识符);SQLite 用 COLLATE BINARY(其 CAST
# AS BINARY 语义不符)。WA 保持最近活跃优先。
dialect = session.bind.dialect.name if session.bind is not None else ""
if dialect == "mysql":
owner_order = sa.literal_column(
"CAST(chat_group.owner_account_id AS BINARY)"
).asc()
else:
owner_order = ChatGroup.owner_account_id.collate("BINARY").asc()
list_stmt = (
list_stmt.order_by(
ChatGroup.owner_account_id.collate("BINARY").asc(),
owner_order,
ChatGroup.room_id.asc(),
)
.limit(page_size)