You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python实现Telegram Bot周期性消息遇409冲突错误求排查

Telegram Bot 409冲突错误排查

我尝试实现一个Telegram Bot,让账号定期接收更新消息,但执行时遇到如下错误:

telebot.apihelper.ApiTelegramException: A request to the Telegram API was unsuccessful. Error code: 409. Description: Conflict: terminated by other getUpdates request; make sure that only one bot instance is running

我的代码如下:

import threading

import telebot
import Consts

from mypackage.ProcessManager import ProcessManager


bot = telebot.TeleBot(Consts.bot_token, threaded=True)
process_manager = ProcessManager()


@bot.message_handler(commands=['subscribe'])
def subscribe(message):
    chat_id = message.from_user.id
    if not process_manager.has_running_elements(chat_id):
        process_manager.start_process(chat_id=chat_id,
                                  target=send_message,
                                  arg2=chat_id, arg3="Prova")
        bot.reply_to(message, "Perfetto. Da ora riceverai aggiornamenti sulla tua assicurazione")
    else:
        bot.reply_to(message, "Sei già iscritto")


def send_message(chat_id, message: str):
    bot.send_message(chat_id=chat_id, text=message)


bot.infinity_polling()

ProcessManager是一个管理multiprocessing.Process对象的包装类,其start_process函数代码如下:

def start_process(self, chat_id, target, **args):
    new_process = multiprocessing.Process(target=target,
                                      daemon=True,
                                      args=args)
    self.processes_dict[chat_id] = new_process
    new_process.start()

请问我哪里出错了?


错误原因

409错误的核心是多个Telegram Bot实例同时调用getUpdates接口,触发Telegram服务器的冲突判定。

你的代码存在两个关键问题:

  • 未用if __name__ == '__main__':包裹bot.infinity_polling():在Windows系统中,multiprocessing采用spawn模式创建子进程,会重新执行整个脚本的顶层代码。这导致每个子进程都会初始化新的bot实例并启动轮询,多个实例同时请求更新引发冲突。
  • 子进程共享父进程的bot对象:multiprocessing的进程拥有独立内存空间,父进程的bot会被复制到子进程,但Telebot的实例并非进程安全,这种共享会引发包括重复轮询在内的各种问题。

解决方案

方案1:改用线程替代进程

如果你的定时任务仅需发送消息(无需独立CPU资源),线程是更合适的选择——线程共享同一内存空间,不会重复初始化bot实例:
修改ProcessManager的start_process方法,改用threading.Thread:

def start_process(self, chat_id, target, **args):
    new_thread = threading.Thread(target=target,
                                  daemon=True,
                                  args=args)
    self.processes_dict[chat_id] = new_thread
    new_thread.start()

方案2:修复进程模式的问题

若必须使用进程,需做两处修改:

  1. 将bot.infinity_polling()限制在主进程执行:
if __name__ == '__main__':
    bot.infinity_polling()
  1. 在子进程的send_message中单独初始化bot,避免共享父进程实例:
def send_message(chat_id, message: str):
    # 子进程内独立初始化bot
    bot = telebot.TeleBot(Consts.bot_token)
    bot.send_message(chat_id=chat_id, text=message)

额外建议

如果是实现定期推送功能,更推荐使用Telebot内置的telebot.util.repeat装饰器,或threading.Timer来周期性执行任务,无需手动管理进程/线程,从根源避免多实例冲突。


内容的提问来源于stack exchange,提问作者Fabrizio Gabriele

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 23:50:55