from datetime import datetime, timedelta, date from fastapi import APIRouter, Depends, Security from sqlalchemy import func from sqlalchemy.orm import Session from barker.core.config import settings from .tax_report import get_tax from ...models import Voucher, VoucherType, Settlement, SettleOption, Product, Inventory, Kot, SaleCategory from ...schemas.auth import UserToken from ...core.security import get_current_active_user as get_user from ...db.session import SessionLocal router = APIRouter() # Dependency def get_db() -> Session: try: db = SessionLocal() yield db finally: db.close() @router.get("") def get_sale_analysis( s: str = None, f: str = None, db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["sale-report"]), ): start_date = date.today() if s is None else datetime.strptime(s, "%d-%b-%Y").date() finish_date = date.today() if f is None else datetime.strptime(f, "%d-%b-%Y").date() if (date.today() - start_date).days > 5 and "accounts-audit" not in user.permissions: raise ValueError("Accounts Audit") return { "startDate": start_date.strftime("%d-%b-%Y"), "finishDate": finish_date.strftime("%d-%b-%Y"), "amounts": ( get_sale(start_date, finish_date, db) + [{"name": "--", "amount": 0}] + get_settlements(start_date, finish_date, db) + [{"name": "--", "amount": 0}] + get_tax(start_date, finish_date, db) ), } def get_sale(s: date, f: date, db: Session): start_date = s + timedelta(minutes=settings.NEW_DAY_OFFSET_MINUTES) finish_date = f + timedelta(days=1, minutes=settings.NEW_DAY_OFFSET_MINUTES) list_ = ( db.query(SaleCategory.name, func.sum(Inventory.net)) .join(Inventory.kot) .join(Kot.voucher) .join(Inventory.product) .join(Product.sale_category) .filter( Voucher.date >= start_date, Voucher.date <= finish_date, Voucher.voucher_type == VoucherType.REGULAR_BILL.value, ) .group_by(SaleCategory.name) .order_by(SaleCategory.name) .all() ) total = 0 info = [] for gt, am in list_: total += am info.append({"name": gt, "amount": am}) return info + [{"name": "Total Settled", "amount": total}] def get_settlements(s: date, f: date, db: Session): start_date = s + timedelta(minutes=settings.NEW_DAY_OFFSET_MINUTES) finish_date = f + timedelta(days=1, minutes=settings.NEW_DAY_OFFSET_MINUTES) list_ = ( db.query(SettleOption.name, func.sum(Settlement.amount)) .join(Voucher.settlements) .join(Settlement.settle_option) .filter(Voucher.date >= start_date, Voucher.date <= finish_date) .group_by(SettleOption.name) .order_by(SettleOption.name) .all() ) total = 0 info = [] for gt, am in list_: total += am info.append({"name": gt, "amount": am}) return info + [{"name": "Total", "amount": total}]