@pavelermolenko

Как отправлять сообщение каждый час?

Суть бота - курс обмена по запросу пользователя, с недавнего времени решил сделать админ - панель, через которую админ сможет менять коэффициент, а также получать список пользователей за последний час. При этом получение списка я хочу сделать не только по запросу, но также и автоматически с часовым интервалом, с последующей очисткой списка. С самой панелькой никаких проблем не возникло, но никак не могу реализовать ежечасное отправление. Вот код:
import asyncio

import requests
from aiogram import Bot, Dispatcher, executor, types
from aiogram.types import InlineKeyboardMarkup, InlineKeyboardButton
from bs4 import BeautifulSoup
import datetime
from apscheduler.schedulers.asyncio import AsyncIOScheduler

EURO_RUB = 'https://finance.yahoo.com/quote/EURRUB%3DX?p=EURRUB%3DX'
headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/111.0.0.0 Safari/537.36'}


coeff = 1.06

def get_value(coeff):
    full_page = requests.get(EURO_RUB, headers=headers)
    soup = BeautifulSoup(full_page.content, 'html.parser')
    convert = soup.findAll("fin-streamer", {"class": "Fw(b) Fz(36px) Mb(-4px) D(ib)"})
    print(convert[0].text)
    beginning = datetime.time(9, 50)
    closing = datetime.time(18, 50)
    curreu = str(round(float(convert[0].text.replace(',', '.'))*coeff, 2))
    currdin = str(round(float(convert[0].text.replace(',', '.'))*coeff/117, 2))
    fin = "Актуальный курс Евро (EUR):\n" + curreu + "\n" + "Актуальный курс Сербского Динара(RSD):\n"+ currdin + "!!Минимальный обмен от 100 евро или 10000 динар!!"
    return fin

print(get_value(coeff))

API_TOKEN = '6285702618:AAHbyuoUBGiJ0v9fmc0QZvZvAwNyFYKkNIo'
bot = Bot(token=API_TOKEN)
dp = Dispatcher(bot)

users_list_1hr = []
users_counter = 0

scheduler = AsyncIOScheduler()


async def send_list(message: types.Message):
    if message.from_user.username == 'pashaborsch':
        await message.answer("Пользователи за последний час:")
        for i in range(0, users_counter):
            await message.answer(users_list_1hr[i])


async def schedule_refresher(message):
    global users_counter, users_list_1hr
    await send_list(message)
    users_list_1hr.clear()
    users_counter = 0


scheduler.add_job(schedule_refresher(types.Message), "interval", seconds=10)

mykb = InlineKeyboardMarkup(row_width=1)
mybt = InlineKeyboardButton(text="Обновить курс", callback_data="refresh")
mykb.add(mybt)


mykb_adm = InlineKeyboardMarkup(row_width=1)
bt_adm = InlineKeyboardButton(text="Админская панель", callback_data="adm")
mykb_adm.add(bt_adm)


panel = InlineKeyboardMarkup(row_width=1)
panel_bt1 = InlineKeyboardButton(text="Изменить коэффициент", callback_data="edit")
panel_bt2 = InlineKeyboardButton(text="Назад", callback_data="back")
panel_bt3 = InlineKeyboardButton(text="Список пользователей за последний час", callback_data="get_list")
panel.add(panel_bt1, panel_bt2, panel_bt3)


@dp.message_handler(commands=['start', 'refresh'])
async def cmd_start(message: types.Message):
    print(message.from_user.username)
    await message.reply(get_value(coeff), reply_markup=mykb)
    def users_list_check(message: types.Message):
        global users_counter
        k = 0
        if message.from_user.username != 'pashaborsch':
            for i in range(0, users_counter ):
                if message.from_user.username == users_list_1hr[i]:
                    k = k+1

        if k == 0 and message.from_user.username != 'pashaborsch':
            users_list_1hr.append(message.from_user.username)
            users_counter = users_counter + 1

        print('\n'.join(str(k)))
        print('\n'.join(str(users_counter)))

    users_list_check(message)

    print(message.from_user.username)
    if message.from_user.username == 'pashaborsch':
        await message.answer("Нажмите для доступа к админской панели:", reply_markup=mykb_adm)


@dp.callback_query_handler(text="refresh")
async def send_welcome(query: types.CallbackQuery):
    print(query.from_user.username)
    if query.message.text != get_value(coeff):
        await query.message.edit_text(get_value(coeff), reply_markup=mykb)

    def users_list_check(query: types.CallbackQuery):
        global users_counter
        k = 0
        if query.from_user.username != 'pashaborsch':
            for i in range(0, users_counter):
                if query.from_user.username == users_list_1hr[i]:
                    k = k + 1

        if k == 0 and query.from_user.username != 'pashaborsch' :
            users_list_1hr.append(query.from_user.username)
            users_counter = users_counter + 1

        print('\n'.join(str(k)))
        print('\n'.join(str(users_counter)))

    users_list_check(query)
    date = (datetime.datetime.now() + datetime.timedelta(hours=-1)).strftime("%d/%m/%Y, %H:%M")
    await query.answer("Курс обновлен " + date)


@dp.callback_query_handler(text="adm")
async def admin_kb(query: types.CallbackQuery):
    perc = round(((coeff-1)*100), 2)
    await query.message.answer("Текущий коэффициент = " + str(perc) + "\n", reply_markup=panel)


@dp.callback_query_handler(text="edit")
async def edit(query: types.CallbackQuery):
    await query.message.answer("Введите новый коэффициент:")


@dp.callback_query_handler(text="back")
async def back(query: types.CallbackQuery):
        await query.message.answer(get_value(coeff), reply_markup=mykb)
        print(query.from_user.username)
        if query.from_user.username == 'pashaborsch':
            await query.message.answer("Нажмите для доступа к админской панели:", reply_markup=mykb_adm)


@dp.callback_query_handler(text="get_list")
async def get_list(query: types.CallbackQuery):
    print('\n'.join(users_list_1hr))
    if query.from_user.username == 'pashaborsch':
        await query.message.answer("Пользователи (" + str(users_counter) +") за последний час:")
        for i in range(0, users_counter):
            await query.message.answer("@" + users_list_1hr[i])


@dp.message_handler()
async def coeff_handler(message: types.Message):
    def check():
        try:
            float(message.text)
            return True
        except ValueError:
            return False

    if check():
        global coeff
        coeff = float(message.text)/100+1
        date = (datetime.datetime.now() + datetime.timedelta(hours=-1)).strftime("%d/%m/%Y, %H:%M")
        await message.answer("Коэффициент обновлен " + date)
    else:
        await message.reply("Ошибка ввода, попробуйте еще раз:")


scheduler.start()
if __name__ == '__main__':
    executor.start_polling(dp, skip_updates=True)


При запуске выдает ошибку:
Traceback (most recent call last):
  File "C:\Users\Pavel\PycharmProjects\pythonProject2\main.py", line 54, in <module>
    scheduler.add_job(schedule_refresher(types.Message), "interval", seconds=10)
  File "C:\Users\Pavel\PycharmProjects\pythonProject2\venv\lib\site-packages\apscheduler\schedulers\base.py", line 438, in add_job
    job = Job(self, **job_kwargs)
  File "C:\Users\Pavel\PycharmProjects\pythonProject2\venv\lib\site-packages\apscheduler\job.py", line 49, in __init__
    self._modify(id=id or uuid4().hex, **kwargs)
  File "C:\Users\Pavel\PycharmProjects\pythonProject2\venv\lib\site-packages\apscheduler\job.py", line 170, in _modify
    raise TypeError('func must be a callable or a textual reference to one')
TypeError: func must be a callable or a textual reference to one
sys:1: RuntimeWarning: coroutine 'schedule_refresher' was never awaited


Подскажите, пожалуйста, что я делаю не так и насколько сильно я туплю?
  • Вопрос задан
  • 117 просмотров
Пригласить эксперта
Ответы на вопрос 1
RimMirK
@RimMirK
Вроде человек. Вроде учусь. Вроде пайтону
насколько сильно я туплю?
довольно сильно
await scheduler.add_job(...)
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы