如何多次复用同一session的Telethon客户端避免数据库锁定错误
问题根因
报错本质是session文件锁冲突:
- 你每次调用
in_channel()都会新建独立事件循环、新建TelegramClient实例指向同一个john.session文件 - 上一次函数执行结束后,没有主动断开客户端连接,sqlite格式的session文件的写入锁没有被释放
- 第二次调用时新的客户端实例尝试访问被锁的session文件,直接触发
database is locked错误
修复方案(单session复用客户端)
不需要创建多个session,只需要把客户端实例、事件循环的初始化逻辑从单次调用逻辑中抽离,全局只初始化一次客户端,所有操作复用同一个连接即可,修改后可正常连续调用:
from telethon import TelegramClient import asyncio api_id = "" api_hash = "" session = "john" username = 'Hello_World' # For Example # 全局仅初始化一次TelegramClient实例,不重复创建 client = TelegramClient(session, api_id, api_hash) async def do_search(): entity = await client.get_entity("https://t.me/ahsan_alhadeeth") search_user = await client.get_participants(entity, search=username) print(search_user) return search_user def in_channel(): # 复用全局事件循环执行查询逻辑,不新建循环 loop.run_until_complete(do_search()) if __name__ == "__main__": # 全局仅初始化一次事件循环、启动一次客户端 loop = asyncio.new_event_loop() asyncio.set_event_loop(loop) loop.run_until_complete(client.start()) # 连续多次调用,复用同一个客户端连接、同一个session,不会触发锁冲突 in_channel() in_channel() # 所有操作执行完成后主动断开连接,释放session文件锁 loop.run_until_complete(client.disconnect()) loop.close()
额外注意事项
- 同一个session文件同一时间只能被一个
TelegramClient实例占用,只要前一个实例没有执行disconnect()释放锁,新的实例访问就会报锁错误 - 如果需要在不同代码段执行Telegram操作,直接传递已经初始化好的client对象即可,不要重复调用
TelegramClient()用同一个session路径创建新实例 - 不要频繁创建销毁事件循环和客户端实例,会额外触发连接建立、session读写的开销,复用长连接的执行效率更高
内容的提问来源于stack exchange,提问作者Othman Alkhatib
相关产品推荐
相关产品推荐

