Files
backend/app/routes/subscription_routes.py

117 lines
4.8 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

from typing import List
from fastapi import APIRouter, HTTPException, Depends
from pydantic import BaseModel
from app.services.db_manager import DatabaseManager
from instance.configdb import get_database_manager
from uuid import UUID
import logging
from sqlalchemy.exc import SQLAlchemyError
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
router = APIRouter()
class BuySubscriptionRequest(BaseModel):
telegram_id: int
plan_id: str
class SubscriptionResponse(BaseModel):
id: str
plan: str
vpn_server_id: str
expiry_date: str
created_at: str
updated_at: str
# Эндпоинт для покупки подписки
@router.post("/subscription/buy", response_model=dict)
async def buy_subscription(
request_data: BuySubscriptionRequest,
database_manager: DatabaseManager = Depends(get_database_manager)
):
"""
Покупка подписки.
"""
try:
result = await database_manager.buy_sub(request_data.telegram_id, request_data.plan_id)
if result == "ERROR":
raise HTTPException(status_code=500, detail="Failed to buy subscription")
elif result == "INSUFFICIENT_FUNDS":
raise HTTPException(status_code=400, detail="Insufficient funds")
elif result == "TARIFF_NOT_FOUND":
raise HTTPException(status_code=400, detail="Tariff not found")
elif result == "ACTIVE_SUBSCRIPTION_EXISTS":
raise HTTPException(status_code=400, detail="User already had subscription",)
return {"message": "Subscription purchased successfully"}
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
# Эндпоинт для получения последней подписки
@router.get("/subscription/{user_id}/last", response_model=SubscriptionResponse)
async def last_subscription(user_id: UUID, database_manager: DatabaseManager = Depends(get_database_manager)):
"""
Возвращает последнюю подписку пользователя.
"""
logger.info(f"Получение последней подписки для пользователя: {user_id}")
try:
subscriptions = await database_manager.last_subscriptions(user_id=str(user_id), limit=1)
if not subscriptions:
logger.warning(f"Подписки для пользователя {user_id} не найдены")
raise HTTPException(status_code=404, detail="No subscriptions found")
sub = subscriptions[0]
return {
"id": sub.id,
"plan": sub.plan,
"vpn_server_id": sub.vpn_server_id,
"expiry_date": sub.expiry_date.isoformat(),
"created_at": sub.created_at.isoformat(),
"updated_at": sub.updated_at.isoformat(),
}
except SQLAlchemyError as e:
logger.error(f"Ошибка базы данных при получении подписки для пользователя {user_id}: {e}")
raise HTTPException(status_code=500, detail="Database error")
except Exception as e:
logger.error(f"Неожиданная ошибка: {e}")
raise HTTPException(status_code=500, detail=str(e))
@router.get("/subscriptions/{user_id}", response_model=List[SubscriptionResponse])
async def get_subscriptions(user_id: UUID, database_manager: DatabaseManager = Depends(get_database_manager)):
"""
Возвращает список подписок пользователя.
"""
logger.info(f"Получение подписок для пользователя: {user_id}")
try:
# Получаем подписки без ограничений или с указанным лимитом
subscriptions = await database_manager.last_subscriptions(user_id=str(user_id))
if not subscriptions:
logger.warning(f"Подписки для пользователя {user_id} не найдены")
raise HTTPException(status_code=404, detail="No subscriptions found")
# Формируем список подписок для ответа
return [
{
"id": sub.id,
"plan": sub.plan,
"vpn_server_id": sub.vpn_server_id,
"expiry_date": sub.expiry_date.isoformat(),
"created_at": sub.created_at.isoformat(),
"updated_at": sub.updated_at.isoformat(),
}
for sub in subscriptions
]
except SQLAlchemyError as e:
logger.error(f"Ошибка базы данных при получении подписок для пользователя {user_id}: {e}")
raise HTTPException(status_code=500, detail="Database error")
except Exception as e:
logger.error(f"Неожиданная ошибка: {e}")
raise HTTPException(status_code=500, detail=str(e))