【问题标题】:RuntimeWarning: coroutine 'take_message' was never awaited task(*args, **kwargs)RuntimeWarning:协程“take_message”从未等待任务(*args,**kwargs)
【发布时间】:2020-06-05 15:17:13
【问题描述】:

我编写了一个机器人,它可以与 Telethont 和 Telebot 一起使用。远程机器人需要在电报中收听机器人,他发送命令。电视节目需要收听外星频道,并解析帖子。我想增加一个机会,那就是增加很多听众。但出现错误: /home/home/.local/lib/python3.6/site-packages/telebot/util.py:60: RuntimeWarning: coroutine 'take_message' was never awaited task(*args, **kwargs)

如何解决这个错误?

主要代码:

# -*- coding: utf-8 -*-
import telebot
import asyncio

from telegram_client import TelegramSession as ts

api_id = ********************** # этот id вы получаете при создание приложения
api_hash = '***********************' # и этот тоже
username = '***************' # ваше имя в тг
id_channel = -***************** # id вашего канала
token = '********************' # токен вашего бота

bot = telebot.TeleBot(token)
client = ts(api_id,api_hash,username)

@bot.message_handler(content_types=['text'])
async def take_message(message):
  if '@' in message.text and ',' in message.text:
    channels = message.text.split(',')
    my_channel = channels[-1]
    parse_channel = channels[0:-1]
    await client.add_task(parse_channel,my_channel)
  else:
    return bot.send_message(message.chat.id,'<b>Проверьте правильность ввода!</b>',parse_mode='html')

if __name__ == '__main__':
  bot.polling(none_stop=True)

对模块电报客户端进行编码:

from telethon import TelegramClient,sync,events,utils
import asyncio

class TelegramSession:
  def __init__(self,api_id,api_hash,username):
    self.__loop = asyncio.new_event_loop()
    asyncio.set_event_loop(self.__loop)
    self.client = TelegramClient(username, api_id, api_hash,loop=self.__loop)
    self.client.start()

  async def handler_channel(self,parse_channel,my_channel):
    #print(parse_channel)
    @self.client.on(events.NewMessage(chats=parse_channel))
    async def normal_handler(event):
      await self.client.send_message(my_channel,event.message)

  async def list_tasks(self):
    pass

  async def add_task(self,parse_channel,my_channel):
    print(parse_channel)
    await self.__loop.create_task(self.handler_channel(parse_channel,my_channel))

  async def stop_task(self,something):
    pass

  def run_until(self):
    self.client.run_until_disconnected()

【问题讨论】:

    标签: python python-3.x telethon


    【解决方案1】:

    您似乎在这里混合了两个框架,telebottelethontelethon 基于 async-await 语法(异步代码),而 telebot 不是(同步代码)。

    异步和同步代码不能很好地协同工作并且不能轻易相互调用的事实一直是对在 Python 中引入 async-await 的主要批评。

    因此问题是你有:

    async def take_message(message):
        ...
        await client.add_task(parse_channel,my_channel)
    

    telebot 期望时:

    def take_message(message):
        # ...and NO 'await's inside function body!
    

    couuuuld 尝试将您在take_message 中启动的任务添加到同步代码中telethon 的事件循环(使用loop.create_task),但我不建议这样做。相反,我会尝试只使用一个框架来完成您需要做的事情,而不是同时使用两者。

    【讨论】:

    • 那么,如果我使用telebot.AsyncTelebot,那会改变什么吗?
    • 好的,但是telethon 不能与电报中的机器人一起工作。是吗?如果是,那么如何在电报中收听机器人?
    • 我猜telebot.AsyncTelebot 无济于事,因为您最终会得到两个单独的事件循环。
    • 我不知道telethontelebot 有哪些功能。您必须阅读文档以确保。但是您的应用程序看起来很简单,所以我猜其中至少有一个具有该功能。
    • 哦……伙计,非常感谢))我在 Telethon 方法中找到了,它与电报机器人一起使用)docs.telethon.dev/en/latest/concepts/botapi-vs-mtproto.html
    猜你喜欢
    • 2021-11-24
    • 2018-10-26
    • 2021-10-22
    • 2019-12-15
    • 2021-10-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-10
    相关资源
    最近更新 更多