Программа не выходит из стейта VKBottle
from vkbottle.bot import Message
from vkbottle import Keyboard, KeyboardButtonColor, \
Text, OpenLink, Bot
from jetorm.utils import hash
from connect import db
from keyboards import admin_keyboard, mailing_keyboard
from states import MailingData, ctx
bp = Bot(token=token)
bp.labeler.vbml_ignore_case = True
@bp.on.private_message(text="/admin")
async def admin_commands_handler(message: Message):
if db.find_one('users', '`isAdmin` = 1 AND `user_id` = ?', str(message.from_id)):
admin_name = db.read_one('users', ('first_name',), '`user_id` = ?', str(message.from_id))[0][0]
await message.answer(f"Здравствуйте, {admin_name}! Вот ваша админ-панель:", keyboard=admin_keyboard)
else:
await message.answer("Вы не администратор!")
@bp.on.private_message(payload={"cmd": "create_mailing"})
async def mailing_handler(message: Message):
if db.find_one('users', '`isAdmin` = 1 AND `user_id` = ?', str(message.from_id)):
await bp.state_dispenser.set(message.peer_id, MailingData.TEXT)
return "Введите текст для рассылки:"
else:
await message.answer("Вы не администратор!")
@bp.on.private_message(state=MailingData.TEXT)
async def text_handler(message: Message):
ctx.set("text", message.text)
await bp.state_dispenser.set(message.peer_id, MailingData.IMAGE)
await message.answer("Загрузите картинку (необязательно):")
@bp.on.private_message(state=MailingData.IMAGE)
async def image_handler(message: Message):
ctx.set("image", "")
try:
ctx.set("image", message.attachments[0].photo.sizes[-5].url)
except Exception:
ctx.delete("image")
text = ctx.get("text")
image = ctx.get("image")
post_id = hash(str(message.from_id))[:10]
db.insert('mailing', {
'text': text,
'image_url': image,
'user_id': message.from_id,
'post_id': post_id
})
return f"Рассылка готова! ID: {post_id}\nНапишите /post <id>"
@bp.on.private_message(text=["/post <item>", "/post"])
async def post_handler(message: Message, item=None):
print("="*50)
print(db.find_one('mailing', '`post_id` = ?', item))
print("="*50)
await message.answer(f"{item}")
Проблема в стейтах, когда мне прилетает сообщение, что рассылка готова, я пишу /post id (где id идентификационный номер поста выдаваемый в конце стейта) и стейт снова пишет, что рассылка готова. Вопрос: как выйти из стейта?. Я написал return везде в стейтах.
файл states.py
from vkbottle_types import BaseStateGroup
from vkbottle import CtxStorage
ctx = CtxStorage()
class MailingData(BaseStateGroup):
TEXT = 0
IMAGE = 1
Ответы (1 шт):
Автор решения: 0xmeow
→ Ссылка
У вас в image_handler обрабатывается, когда state=MailingData.IMAGE, а внутри вы state не меняете. И он снова обрабатывается, поскольку state остался прежним и стоит раньше post_handler.
Есть два решения:
- Изменять
stateвнутриimage_handler. - Изменить порядок хендлеров.
Можно использовать одновременно оба решения.