python-telegram-bot document:
Since v20.0, python-telegram-bot is built on top of Pythons asyncio module. Because asyncio is in general single-threaded, python-telegram-bot does currently not aim to be thread-safe.
If bot command execute some long time work,will block the whole BOT recieve and send message.So I want use wrapper to thead bot command task.
The follow is my code. test command can normal execure.
But I get exception object NoneType can’t be used in ‘await’ expression.
So somewhere should be have worng.
def asyncbot(mythread):
def wrapper(*args, **kwargs):
def wrap_async_func(*args, **kwargs):
asyncio.run(mythread(*args, **kwargs))
_thread = Thread(target=wrap_async_func, args=args, kwargs=kwargs)
_thread.start()
return wrapper
@asyncbot
async def test(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
sleep(20)
logging:
An exception was raised while handling an update update =
"None"
context.chat_data = None
context.user_data = None
Traceback (most recent call last):
File "/usr/local/lib/python3.10/dist-packages/telegram/ext/_jobqueue.py", line 898, in _run
await self.callback(context)
TypeError: object NoneType can't be used in 'await' expression
2
Answers
Yes.Thx you suggestion. But Now my command task have many sync request http code. It is hard to change to async code. Use thread is current better solution for us. So if use thread, how to solve "object NoneType can't be used in 'await' expression" exception?
The issue is that your decorator does not return a coroutine function. PTB expects that all callback function are corutine functions (
async def
) that can beawait
-ed, so your handler must return such a function.However, I do want to point out that starting a thread seems not to be the bestion solution. Alternatives to consider:
asycnio.sleep
instead oftime.sleep
)loop.run_in_excutor
Disclaimer: I’m currently the maintainer of
python-telegram-bot
.