Telegram机器人代码异常:点击按钮后无法转发URL至目标Bot
问题:Telegram机器人点击按钮后无法读取更新的URL并转发
代码片段
@events.register(events.NewMessage(chats='tubot')) async def mi_handler(event): client = event.client if 'A big' in event.raw_text: async for message in client.iter_messages('tubot', limit=1, from_user='tubot'): await message.click(0) url = event.message.buttons[0][0].url print(url) await event.client.send_message('mybot', url.split('=')[1])
问题描述
预期功能:当“tubot”收到包含'A big'的消息时,点击消息内按钮解锁URL,再提取URL中“=”后的内容发送至“mybot”。
实际异常:
- 消息刚抵达“tubot”时,代码能成功点击按钮,但无法完成转发操作;
- 手动将已解锁按钮的消息转发至“tubot”时,代码可正常提取URL并转发到“mybot”。
已尝试的调试方法
- 在点击按钮与读取URL之间添加
await asyncio.sleep(0.2),无效; - 将点击按钮和转发操作拆分为两个独立处理函数,无效;
- 创建中转群组:让代码点击“tubot”的消息后转发至群组,再用另一代码读取群组内已解锁消息并转发URL到“mybot”,仍无效。但手动转发已解锁消息到群组时,代码可正常处理。
解决方案
问题核心:点击按钮后,原event.message是初始状态的缓存对象,不会自动更新为按钮解锁后的消息内容。刚收到消息就点击按钮时,读取的还是未解锁的旧数据;手动转发的是已经更新后的消息,因此能正常读取URL。
修改后的代码
import asyncio @events.register(events.NewMessage(chats='tubot')) async def mi_handler(event): client = event.client if 'A big' in event.raw_text: # 记录当前触发事件的消息ID,精准定位目标消息 target_msg_id = event.message.id # 点击按钮 await event.message.click(0) # 重试获取更新后的消息,确保服务器同步数据 updated_msg = None for _ in range(3): updated_msg = await client.get_messages('tubot', ids=target_msg_id) # 检查按钮是否已解锁并存在URL if updated_msg.buttons and updated_msg.buttons[0][0].url: break await asyncio.sleep(0.3) if not updated_msg or not updated_msg.buttons[0][0].url: print("点击按钮后无法获取更新的URL") return url = updated_msg.buttons[0][0].url print(url) await client.send_message('mybot', url.split('=')[1])
关键改进点
- 通过消息ID精准获取目标消息,避免
iter_messages可能拿到其他消息的问题; - 增加重试机制,等待服务器同步按钮点击后的消息更新;
- 直接获取最新版本的消息对象,不再依赖原
event.message的缓存。
额外建议
- 添加异常捕获,避免因按钮结构变化、URL格式异常导致代码崩溃;
- 若重试后仍无法获取URL,可适当延长等待时间,或检查机器人是否有读取该聊天消息的完整权限。
内容的提问来源于stack exchange,提问作者Elvis
相关产品推荐
相关产品推荐

