separated clients handlers, cart->checkout ppline
This commit is contained in:
164
handlers/client/products.py
Normal file
164
handlers/client/products.py
Normal file
@@ -0,0 +1,164 @@
|
||||
import os
|
||||
from re import Match
|
||||
from aiogram import Router, F
|
||||
from aiogram.types import CallbackQuery, FSInputFile
|
||||
from aiogram.fsm.context import FSMContext
|
||||
from sqlalchemy.ext.asyncio import AsyncSession
|
||||
|
||||
from config import PAGE_SIZE
|
||||
from misc.kb.client import (
|
||||
render_product_interactions,
|
||||
render_products,
|
||||
)
|
||||
from misc.texts import get_product_description
|
||||
from repositories.categories import CategoriesRepository
|
||||
from repositories.products import ProductRepository
|
||||
from services.orders import OrderService
|
||||
|
||||
router = Router()
|
||||
|
||||
|
||||
@router.callback_query(
|
||||
F.data.regexp(r"products:(?P<category_id>.*):(?P<page_id>\d+)").as_(
|
||||
"pagination_match"
|
||||
)
|
||||
)
|
||||
async def products_pagination(
|
||||
cb: CallbackQuery,
|
||||
state: FSMContext,
|
||||
pagination_match: Match[str],
|
||||
session: AsyncSession,
|
||||
products_repo: ProductRepository,
|
||||
categories_repo: CategoriesRepository,
|
||||
):
|
||||
await state.clear()
|
||||
|
||||
pagination_data = pagination_match.groupdict()
|
||||
category_id = int(pagination_data.get("category_id"))
|
||||
category = await categories_repo.get_category_by_id(session, category_id)
|
||||
page_id = int(pagination_data.get("page_id", 0))
|
||||
|
||||
products = await products_repo.get_product_by_category(
|
||||
session, category_id, limit=PAGE_SIZE + 1, offset=page_id * PAGE_SIZE
|
||||
)
|
||||
products_len = len(products)
|
||||
|
||||
await cb.message.edit_reply_markup(
|
||||
reply_markup=render_products(
|
||||
products[:PAGE_SIZE],
|
||||
parent_id=category.parent_id,
|
||||
cat_id=category_id,
|
||||
page=page_id,
|
||||
show_prev=page_id > 0,
|
||||
show_next=products_len > PAGE_SIZE,
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
@router.callback_query(F.data.startswith("product:"))
|
||||
async def product_card(
|
||||
cb: CallbackQuery,
|
||||
state: FSMContext,
|
||||
session: AsyncSession,
|
||||
products_repo: ProductRepository,
|
||||
order_service: OrderService,
|
||||
):
|
||||
await state.clear()
|
||||
|
||||
product_id = int(cb.data.split(":")[1])
|
||||
product = await products_repo.get_product_by_id(session, product_id)
|
||||
|
||||
order_item = await order_service.get_cart_product_amount(
|
||||
session, customer=cb.from_user.id, product_id=product_id
|
||||
)
|
||||
|
||||
if product.file_id:
|
||||
await cb.message.delete()
|
||||
|
||||
msg = await cb.message.answer_photo(
|
||||
product.file_id,
|
||||
caption=get_product_description(product),
|
||||
reply_markup=render_product_interactions(
|
||||
product_id=product.id,
|
||||
category_id=product.category_id,
|
||||
show_cart=bool(order_item),
|
||||
cart_amount=order_item,
|
||||
),
|
||||
)
|
||||
return
|
||||
|
||||
if not os.path.isfile(product.img_path):
|
||||
await cb.message.edit_text(
|
||||
get_product_description(product),
|
||||
reply_markup=render_product_interactions(
|
||||
product_id=product.id,
|
||||
category_id=product.category_id,
|
||||
show_cart=bool(order_item),
|
||||
cart_amount=order_item,
|
||||
),
|
||||
)
|
||||
return
|
||||
|
||||
await cb.message.delete()
|
||||
msg = await cb.message.answer_photo(
|
||||
FSInputFile(product.img_path),
|
||||
caption=get_product_description(product),
|
||||
reply_markup=render_product_interactions(
|
||||
product_id=product.id,
|
||||
category_id=product.category_id,
|
||||
show_cart=bool(order_item),
|
||||
cart_amount=order_item,
|
||||
),
|
||||
)
|
||||
|
||||
if not msg.photo:
|
||||
return # TODO: Add logging
|
||||
|
||||
await products_repo.add_product_file_id(
|
||||
session, product_id, file_id=msg.photo[-1].file_id
|
||||
)
|
||||
|
||||
|
||||
@router.callback_query(F.data.startswith("cart_action:"))
|
||||
async def add_to_cart(
|
||||
cb: CallbackQuery,
|
||||
state: FSMContext,
|
||||
session: AsyncSession,
|
||||
order_service: OrderService,
|
||||
products_repo: ProductRepository,
|
||||
):
|
||||
await state.clear()
|
||||
|
||||
action = cb.data.split(":")[1]
|
||||
product_id = int(cb.data.split(":")[2])
|
||||
product = await products_repo.get_product_by_id(session, product_id)
|
||||
show_cart = True
|
||||
|
||||
if action == "add":
|
||||
quantity = await order_service.add_to_cart(
|
||||
session, customer=cb.from_user.id, product_id=product_id
|
||||
)
|
||||
elif action == "remove":
|
||||
quantity = await order_service.remove_from_cart(
|
||||
session, customer=cb.from_user.id, product_id=product_id
|
||||
)
|
||||
show_cart = bool(quantity)
|
||||
else:
|
||||
show_cart = False
|
||||
quantity = 0
|
||||
await order_service.clear_cart_item(
|
||||
session, customer=cb.from_user.id, product_id=product_id
|
||||
)
|
||||
|
||||
try:
|
||||
await cb.message.edit_reply_markup(
|
||||
reply_markup=render_product_interactions(
|
||||
product_id=product_id,
|
||||
category_id=product.category_id,
|
||||
show_cart=show_cart,
|
||||
cart_amount=quantity,
|
||||
)
|
||||
)
|
||||
except Exception as e:
|
||||
await cb.answer("🍃")
|
||||
raise e
|
||||
Reference in New Issue
Block a user