From 4f161349557878d4c04547d069fe4cb75de65ebf Mon Sep 17 00:00:00 2001 From: v6ole Date: Tue, 12 May 2026 17:59:10 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E6=9C=80=E6=96=B0=E5=85=AC=E5=91=8A?= =?UTF-8?q?=E9=98=B2=E9=87=8D=E5=85=A5=E8=A6=86=E7=9B=96=E6=95=B4=E4=B8=AA?= =?UTF-8?q?=E5=87=BD=E6=95=B0=EF=BC=8C=E6=8E=A8=E9=80=81=E6=94=B9=E4=B8=BA?= =?UTF-8?q?=E6=97=B6=E9=97=B4=E5=8D=87=E5=BA=8F=E9=97=B4=E9=9A=941?= =?UTF-8?q?=E7=A7=92?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 防重入锁移到函数入口,60秒内重复点击直接忽略,避免企微重试导致重复推送 - 取最新6条后按 publish_date 升序推送,企微向上滑即为时间正序 - 每条间隔1秒发送 Co-Authored-By: Claude Sonnet 4.6 --- app/wechat/handler.py | 31 +++++++++++++++++-------------- 1 file changed, 17 insertions(+), 14 deletions(-) diff --git a/app/wechat/handler.py b/app/wechat/handler.py index f756465..31f201c 100644 --- a/app/wechat/handler.py +++ b/app/wechat/handler.py @@ -243,24 +243,25 @@ class WeChatMessageHandler: async def _handle_latest_announcements(self, from_user: str) -> str | None: global _last_latest_time from app.api.deps import get_db, get_crawl_service - from sqlalchemy import select, desc, or_ + from sqlalchemy import select, asc, or_ from app.models.announcement import Announcement + # 防重入:60秒内整个函数只执行一次(含推送) + async with _latest_lock: + now = time.monotonic() + if (now - _last_latest_time) < 60: + logger.info("最新公告请求被忽略(防重入)") + return None + _last_latest_time = now + try: - # 防重入:60秒内只爬取一次 - async with _latest_lock: - now = time.monotonic() - do_crawl = (now - _last_latest_time) >= 60 - if do_crawl: - _last_latest_time = now + await self.client.send_text("正在获取最新公告,请稍候...", from_user) + service = get_crawl_service() + await service.run_all() - if do_crawl: - await self.client.send_text("正在获取最新公告,请稍候...", from_user) - service = get_crawl_service() - await service.run_all() - - # 查:广西政采网关键词匹配 + 大化县政府网全部 + # 查:广西政采网关键词匹配 + 大化县政府网全部,取最新6条后按时间升序推送 async for db in get_db(): + from sqlalchemy import select, desc, or_ result = await db.execute( select(Announcement) .where(or_( @@ -276,7 +277,8 @@ class WeChatMessageHandler: await self.client.send_text("暂无公告", from_user) return None - for ann in items: + # 按时间升序推送,企微里向上滑即为时间正序 + for ann in sorted(items, key=lambda a: a.publish_date): title = ann.title if len(ann.title) <= 128 else ann.title[:125] + "..." purchase_name = ann.purchase_name or "" if len(purchase_name) > 25: @@ -285,6 +287,7 @@ class WeChatMessageHandler: source_name = ann.source_name or ann.source_code or "" description = f"{source_name} | {purchase_name} | {time_str}" await self.client.send_textcard(title, description, ann.content_url or "", from_user) + await asyncio.sleep(1) except Exception as e: logger.error(f"查询最新公告失败: {e}") await self.client.send_text("查询失败,请稍后再试", from_user)