Adding more shit

This commit is contained in:
James Pattinson
2025-11-10 15:42:09 +00:00
parent f1c4ff19d6
commit 43b13ef52d
10 changed files with 682 additions and 21 deletions

View File

@@ -4,11 +4,12 @@ from typing import List
from datetime import date, timedelta
from ...core.database import get_db
from ...models.models import Membership, MembershipStatus, User, MembershipTier
from ...models.models import Membership, MembershipStatus, User, MembershipTier, Payment, PaymentStatus
from ...schemas import (
MembershipCreate, MembershipUpdate, MembershipResponse, MessageResponse
)
from ...api.dependencies import get_current_active_user, get_admin_user
from ...services.email_service import email_service
router = APIRouter()
@@ -112,6 +113,11 @@ async def update_membership(
)
update_data = membership_update.model_dump(exclude_unset=True)
was_activated = False
# Check if status is being changed to ACTIVE
if update_data.get("status") == MembershipStatus.ACTIVE and membership.status != MembershipStatus.ACTIVE:
was_activated = True
for field, value in update_data.items():
setattr(membership, field, value)
@@ -119,6 +125,32 @@ async def update_membership(
db.commit()
db.refresh(membership)
# Send activation email if membership was just activated
if was_activated:
try:
# Get the most recent payment for this membership
recent_payment = db.query(Payment).filter(
Payment.membership_id == membership.id,
Payment.status == PaymentStatus.COMPLETED
).order_by(Payment.payment_date.desc()).first()
payment_amount = recent_payment.amount if recent_payment else membership.tier.annual_fee
payment_method = recent_payment.payment_method.value if recent_payment else "N/A"
# Send activation email (non-blocking)
await email_service.send_membership_activation_email(
to_email=membership.user.email,
first_name=membership.user.first_name,
membership_tier=membership.tier.name,
annual_fee=membership.tier.annual_fee,
payment_amount=payment_amount,
payment_method=payment_method,
renewal_date=membership.end_date.strftime("%d %B %Y")
)
except Exception as e:
# Log error but don't fail the membership update
print(f"Failed to send membership activation email: {e}")
return membership

View File

@@ -4,11 +4,12 @@ from typing import List
from datetime import datetime
from ...core.database import get_db
from ...models.models import Payment, PaymentStatus, User, Membership
from ...models.models import Payment, PaymentStatus, User, Membership, MembershipStatus
from ...schemas import (
PaymentCreate, PaymentUpdate, PaymentResponse, MessageResponse
)
from ...api.dependencies import get_current_active_user, get_admin_user
from ...services.email_service import email_service
router = APIRouter()
@@ -114,6 +115,31 @@ async def update_payment(
db.commit()
db.refresh(payment)
# If payment was just marked as completed and has an associated membership,
# activate the membership and send activation email
if (update_data.get("status") == PaymentStatus.COMPLETED and
payment.membership_id and
payment.membership.status == MembershipStatus.PENDING):
# Activate the membership
payment.membership.status = MembershipStatus.ACTIVE
db.commit()
# Send activation email (non-blocking)
try:
await email_service.send_membership_activation_email(
to_email=payment.membership.user.email,
first_name=payment.membership.user.first_name,
membership_tier=payment.membership.tier.name,
annual_fee=payment.membership.tier.annual_fee,
payment_amount=payment.amount,
payment_method=payment.payment_method.value,
renewal_date=payment.membership.end_date.strftime("%d %B %Y")
)
except Exception as e:
# Log error but don't fail the payment update
print(f"Failed to send membership activation email: {e}")
return payment
@@ -152,6 +178,7 @@ async def record_manual_payment(
)
# Verify membership if provided
membership = None
if payment_data.membership_id:
membership = db.query(Membership).filter(
Membership.id == payment_data.membership_id,
@@ -178,4 +205,24 @@ async def record_manual_payment(
db.commit()
db.refresh(payment)
# If payment has an associated membership that's pending, activate it and send email
if membership and membership.status == MembershipStatus.PENDING:
membership.status = MembershipStatus.ACTIVE
db.commit()
# Send activation email (non-blocking)
try:
await email_service.send_membership_activation_email(
to_email=membership.user.email,
first_name=membership.user.first_name,
membership_tier=membership.tier.name,
annual_fee=membership.tier.annual_fee,
payment_amount=payment.amount,
payment_method=payment.payment_method.value,
renewal_date=membership.end_date.strftime("%d %B %Y")
)
except Exception as e:
# Log error but don't fail the payment creation
print(f"Failed to send membership activation email: {e}")
return payment

View File

@@ -7,7 +7,7 @@ from ...models.models import MembershipTier
from ...schemas import (
MembershipTierCreate, MembershipTierUpdate, MembershipTierResponse, MessageResponse
)
from ...api.dependencies import get_current_active_user, get_admin_user
from ...api.dependencies import get_current_active_user, get_admin_user, get_super_admin_user
router = APIRouter()
@@ -47,10 +47,10 @@ async def get_membership_tier(
@router.post("/", response_model=MembershipTierResponse, status_code=status.HTTP_201_CREATED)
async def create_membership_tier(
tier_data: MembershipTierCreate,
current_user = Depends(get_admin_user),
current_user = Depends(get_super_admin_user),
db: Session = Depends(get_db)
):
"""Create a new membership tier (admin only)"""
"""Create a new membership tier (super admin only)"""
# Check if tier with same name exists
existing_tier = db.query(MembershipTier).filter(
MembershipTier.name == tier_data.name
@@ -74,10 +74,10 @@ async def create_membership_tier(
async def update_membership_tier(
tier_id: int,
tier_update: MembershipTierUpdate,
current_user = Depends(get_admin_user),
current_user = Depends(get_super_admin_user),
db: Session = Depends(get_db)
):
"""Update membership tier (admin only)"""
"""Update membership tier (super admin only)"""
tier = db.query(MembershipTier).filter(MembershipTier.id == tier_id).first()
if not tier:
raise HTTPException(
@@ -99,10 +99,10 @@ async def update_membership_tier(
@router.delete("/{tier_id}", response_model=MessageResponse)
async def delete_membership_tier(
tier_id: int,
current_user = Depends(get_admin_user),
current_user = Depends(get_super_admin_user),
db: Session = Depends(get_db)
):
"""Delete membership tier (admin only)"""
"""Delete membership tier (super admin only)"""
tier = db.query(MembershipTier).filter(MembershipTier.id == tier_id).first()
if not tier:
raise HTTPException(