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

Python开发Telegram Bot:ConversationHandler与Filters模块异常

问题原因

你的代码基于python-telegram-bot v12及更早版本编写,但当前安装的大概率是v13+版本。新版本对模块结构、API做了大幅调整,导致旧代码里的Filters、ConversationHandler等导入和用法直接失效,重装库也解决不了版本不兼容的问题。

解决方案

两种修复方式任选其一:

方式一:降级到兼容的旧版本

卸载当前版本,安装最后一个v12稳定版,无需修改代码即可直接运行:

pip uninstall python-telegram-bot -y
pip install python-telegram-bot==12.8.1

注意:旧版本不再维护,后续可能无法适配Telegram新API功能。

方式二:修改代码适配v13+版本

以下是适配后的完整代码,同时修复了原代码中save_phone_number函数未完成的bug:

import telegram
from telegram import InlineKeyboardButton, InlineKeyboardMarkup
from telegram.ext import (
    Application,
    CommandHandler,
    MessageHandler,
    CallbackQueryHandler,
    ConversationHandler,
    filters
)

# 预测试可选日期
DATES = ["May 1", "May 15", "May 29"]

# 口语测试可选日期
SPEAKING_DAYS = ["Monday", "Tuesday", "Wednesday"]

# 可选时间段
TIME_SLOTS = ["10:00am - 10:12am", "10:12am - 10:24am", "10:24am - 10:36am", "10:36am - 10:48am",
              "10:48am - 11:00am", "11:00am - 11:12am", "11:12am - 11:24am", "11:24am - 11:36am",
              "11:36am - 11:48am", "11:48am - 12:00pm", "2:00pm - 2:12pm", "2:12pm - 2:24pm"]

# 神经元预测试中心群组ID
NEURON_GROUP_ID = "NEURON_GROUP_ID"

# Bot令牌
TOKEN = "YOUR_BOT_TOKEN_HERE"

# 对话状态定义
DATE, TEST_TYPE, NAME, PHONE_NUMBER, SPEAKING_DAY, TIME_SLOT = range(6)


async def start(update, context):
    """启动对话,让用户选择日期"""
    reply_markup = InlineKeyboardMarkup(build_dates_keyboard())
    await update.message.reply_text('欢迎来到神经元预测试中心!请从下方选择测试日期:', reply_markup=reply_markup)
    return DATE


def build_dates_keyboard():
    """构建日期选择键盘"""
    keyboard = [[InlineKeyboardButton(date, callback_data=date)] for date in DATES]
    return keyboard


async def select_date(update, context):
    """保存选中的日期,让用户选择测试类型"""
    query = update.callback_query
    await query.answer()
    context.user_data['date'] = query.data
    keyboard = InlineKeyboardMarkup(build_test_type_keyboard())
    await query.edit_message_text(text=f'已选择日期:{context.user_data["date"]}。请选择测试类型:', reply_markup=keyboard)
    return TEST_TYPE


def build_test_type_keyboard():
    """构建测试类型选择键盘"""
    keyboard = [[InlineKeyboardButton("雅思预测试", callback_data="IELTS Pretest"), 
                 InlineKeyboardButton("CEFR预测试", callback_data="CEFR Pretest")]]
    return keyboard


async def select_test_type(update, context):
    """保存选中的测试类型,让用户输入姓名"""
    query = update.callback_query
    await query.answer()
    context.user_data['test_type'] = query.data
    await query.edit_message_text(text=f'已选择测试类型:{context.user_data["test_type"]}。请输入你的全名:')
    return NAME


async def save_name(update, context):
    """保存姓名,让用户输入手机号"""
    context.user_data['name'] = update.message.text
    await update.message.reply_text('请输入你的手机号码:')
    return PHONE_NUMBER


async def save_phone_number(update, context):
    """保存手机号,让用户选择口语测试日期"""
    context.user_data['phone_number'] = update.message.text
    await update.message.reply_text('请选择口语测试日期(Monday/Tuesday/Wednesday):')
    return SPEAKING_DAY


async def select_speaking_day(update, context):
    """保存口语测试日期,让用户选择时间段"""
    context.user_data['speaking_day'] = update.message.text
    keyboard = InlineKeyboardMarkup(build_time_slots_keyboard())
    await update.message.reply_text('请选择测试时间段:', reply_markup=keyboard)
    return TIME_SLOT


def build_time_slots_keyboard():
    """构建时间段选择键盘"""
    keyboard = [[InlineKeyboardButton(slot, callback_data=slot)] for slot in TIME_SLOTS]
    return keyboard


async def select_time_slot(update, context):
    """保存时间段,发送注册信息到群组,结束对话"""
    query = update.callback_query
    await query.answer()
    context.user_data['time_slot'] = query.data
    registration_info = get_registration_info(context.user_data)
    await context.bot.send_message(chat_id=NEURON_GROUP_ID, text=registration_info)
    await query.edit_message_text(text='感谢选择神经元预测试中心!你的注册已完成,期待你的到来!')
    return ConversationHandler.END


def get_registration_info(user_data):
    """格式化注册信息"""
    info = "新注册信息:\n"
    info += f"测试日期: {user_data['date']}\n"
    info += f"测试类型: {user_data['test_type']}\n"
    info += f"姓名: {user_data['name']}\n"
    info += f"手机号: {user_data['phone_number']}\n"
    info += f"口语测试日期: {user_data['speaking_day']}\n"
    info += f"测试时间段: {user_data['time_slot']}\n"
    return info


async def cancel(update, context):
    """取消对话"""
    await update.message.reply_text('对话已取消,再见!')
    return ConversationHandler.END


def main():
    """启动Bot"""
    application = Application.builder().token(TOKEN).build()

    conv_handler = ConversationHandler(
        entry_points=[CommandHandler('start', start)],
        states={
            DATE: [CallbackQueryHandler(select_date)],
            TEST_TYPE: [CallbackQueryHandler(select_test_type)],
            NAME: [MessageHandler(filters.TEXT & ~filters.COMMAND, save_name)],
            PHONE_NUMBER: [MessageHandler(filters.TEXT & ~filters.COMMAND, save_phone_number)],
            SPEAKING_DAY: [MessageHandler(filters.TEXT & ~filters.COMMAND, select_speaking_day)],
            TIME_SLOT: [CallbackQueryHandler(select_time_slot)]
        },
        fallbacks=[CommandHandler('cancel', cancel)]
    )

    application.add_handler(conv_handler)

    application.run_polling()


if __name__ == '__main__':
    main()

核心修改点:

  1. 替换旧版Updater为v13+的核心入口类Application
  2. Filters改为小写的filters,调整导入路径
  3. 所有消息处理函数添加async关键字,调用API时加await(新版本全面异步)
  4. 补全save_phone_number函数的逻辑,修复变量赋值错误
  5. 用f-string替代format简化字符串拼接
  6. 移除过时的use_context=True参数

若选择方式二,确保安装最新版库:

pip install python-telegram-bot --upgrade

内容的提问来源于stack exchange,提问作者Rakhmatillo Rayimjonov

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.23 18:35:05