N
N
NoKit2021-10-19 16:42:06
Python
NoKit, 2021-10-19 16:42:06

How to implement coroutine threads?

Hello!

I understand multithreading and asynchrony. The goal is simple, the bot has stateful asynchronous methods. I want multiple users to be able to use the bot at the same time. To do this, I decided to implement a multi-threaded launch of the bot.

I tried different ways, but the bot either does not start or does not create threads when accessed by several users at the same time. Help me figure out what's wrong?

Main code:

import asyncio
import time
from concurrent.futures import ThreadPoolExecutor
import logging
import threading
from aiogram import Bot, Dispatcher, executor
from aiogram.contrib.fsm_storage.memory import MemoryStorage
from state_t import register_handlers_choose
import keyboards_t


logger = logging.getLogger(__name__)
logging.basicConfig(
    level=logging.INFO,
    format="%(asctime)s - %(levelname)s - %(name)s - %(message)s",
)
logger.error("Starting bot")
bot = Bot(token="")
dp = Dispatcher(bot, storage=MemoryStorage())

async def worker(dp):
    register_handlers_choose(dp)

async def main(dp):
    futures = [loop.run_in_executor(executor, worker, dp)]
    await asyncio.gather(*futures)
    await dp.start_polling()
    await keyboards_t.set_default_commands(dp)

if __name__ == '__main__':
    start = time.perf_counter()
    executor = ThreadPoolExecutor(max_workers=3)
    loop = asyncio.get_event_loop()
    loop.run_until_complete(main(dp))


Methods:
import time
from aiogram import Dispatcher, types
from aiogram.dispatcher import FSMContext
from aiogram.dispatcher.filters import Text
from aiogram.dispatcher.filters.state import State, StatesGroup
import keyboards_t as kb



class States(StatesGroup):
    w_do = State()

async def start(message: types.Message):
    await message.answer(f"Даров, начнем?", reply_markup=kb.do_menu)
    await States.w_do.set()

async def dodo(message: types.Message, state: FSMContext):
    i = 0
    while i < 20:
        i += 1
        logger.info(time.perf_counter())
        await message.answer(f"{i}")
        time.sleep(5)


async def cmd_cancel(message: types.Message, state: FSMContext):
    await state.finish()
    await message.answer("Отмена", reply_markup=kb.do_menu)

def register_handlers_choose(dp: Dispatcher):
    dp.register_message_handler(start, commands="start", state="*")
    dp.register_message_handler(cmd_cancel, commands="cancel", state="*")
    dp.register_message_handler(dodo, state=States.w_do)

Answer the question

In order to leave comments, you need to log in

1 answer(s)
S
Sergey Gornostaev, 2021-10-19
@sergey-gornostaev

First, in principle, you should not mix asynchrony with multithreading. Second, you don't need it, aiogram is designed to be asynchronous and designed to be used by multiple users at the same time. To do this, it is enough to write the code correctly.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question