customerwebsitebackend/orders/views.py
vickytechkey ba49657163
All checks were successful
Deploy Beta (NATIVE) / deploy (push) Successful in 19s
integrated seller items
2026-08-14 19:24:24 +05:30

215 lines
8.1 KiB
Python

import logging
audit_logger = logging.getLogger('audit')
from rest_framework import status, permissions
from rest_framework.response import Response
from rest_framework.views import APIView
from .models import Cart, CartItem, Order, SellerOrder
from .serializers import CartSerializer, OrderSerializer
from products.models import Product
import uuid
from django.utils.timezone import now
class CartView(APIView):
permission_classes = [permissions.IsAuthenticated]
def get_cart(self, user):
cart, created = Cart.objects.get_or_create(user=user)
return cart
def get(self, request):
cart = self.get_cart(request.user)
serializer = CartSerializer(cart)
return Response(serializer.data)
def post(self, request):
cart = self.get_cart(request.user)
product_id = request.data.get('product_id')
quantity = int(request.data.get('quantity', 1))
try:
product = Product.objects.get(id=product_id)
except Product.DoesNotExist:
return Response({"error": "Product not found"}, status=status.HTTP_404_NOT_FOUND)
cart_item, created = CartItem.objects.get_or_create(
cart=cart,
product_id=product_id,
defaults={'price_at_add': product.price, 'quantity': 0}
)
cart_item.quantity += quantity
cart_item.price_at_add = product.price
cart_item.save()
return Response({"message": "Item added to cart"})
class CartItemDetailView(APIView):
permission_classes = [permissions.IsAuthenticated]
def put(self, request, pk):
try:
item = CartItem.objects.get(id=pk, cart__user=request.user)
except CartItem.DoesNotExist:
return Response({"error": "Cart item not found"}, status=status.HTTP_404_NOT_FOUND)
quantity = int(request.data.get('quantity', 1))
if quantity <= 0:
item.delete()
return Response({"message": "Item removed from cart"})
item.quantity = quantity
item.save()
return Response({"message": "Cart updated"})
def delete(self, request, pk):
try:
item = CartItem.objects.get(id=pk, cart__user=request.user)
except CartItem.DoesNotExist:
return Response({"error": "Cart item not found"}, status=status.HTTP_404_NOT_FOUND)
item.delete()
return Response({"message": "Item removed from cart"})
class CheckoutView(APIView):
permission_classes = [permissions.IsAuthenticated]
def post(self, request):
user = request.user
try:
cart = Cart.objects.get(user=user)
except Cart.DoesNotExist:
return Response({"error": "Cart is empty"}, status=status.HTTP_400_BAD_REQUEST)
items = cart.items.all()
if not items.exists():
return Response({"error": "Cart is empty"}, status=status.HTTP_400_BAD_REQUEST)
shipping_address = request.data.get('shipping_address')
if not shipping_address:
return Response({"error": "Shipping address is required"}, status=status.HTTP_400_BAD_REQUEST)
total_amount = sum(item.quantity * item.price_at_add for item in items)
razorpay_order_id = f"order_{uuid.uuid4().hex[:14]}"
# 1. Create a local Customer Order
order = Order.objects.create(
user=user,
total_amount=total_amount,
status='pending',
razorpay_order_id=razorpay_order_id,
shipping_address=shipping_address
)
audit_logger.info(f"AUDIT - Checkout: User '{user.username}' created order ID {order.id} for amount ${total_amount:.2f}.")
# 2. Write to shared SellerOrder (api_order) so sellers get notified of incoming requests
for item in items:
prod = item.product
if prod:
SellerOrder.objects.create(
supplier_id=prod.supplier_id,
order_id=f"{order.id}-{prod.id}",
date=now().date(),
item=prod.title,
quantity=item.quantity,
customer=user.username,
total=item.quantity * item.price_at_add,
status='Pending Acceptance'
)
# Clear Cart
items.delete()
return Response({
"message": "Order initiated",
"order_id": order.id,
"razorpay_order_id": razorpay_order_id,
"amount": float(total_amount)
})
class PaymentSuccessView(APIView):
permission_classes = [permissions.IsAuthenticated]
def post(self, request):
order_id = request.data.get('order_id')
payment_id = request.data.get('razorpay_payment_id')
try:
order = Order.objects.get(id=order_id, user=request.user)
except Order.DoesNotExist:
return Response({"error": "Order not found"}, status=status.HTTP_404_NOT_FOUND)
order.status = 'confirmed'
order.razorpay_payment_id = payment_id
order.save()
audit_logger.info(f"AUDIT - Payment Success: User '{request.user.username}' successfully paid order ID {order.id} (Payment ID: {payment_id}).")
# Update matching SellerOrders status
SellerOrder.objects.filter(order_id__startswith=f"{order.id}-").update(status='Ready to Ship')
return Response({"message": "Payment verified and order confirmed"})
class OrderHistoryView(APIView):
permission_classes = [permissions.IsAuthenticated]
def get(self, request):
orders = Order.objects.filter(user=request.user).order_by('-placed_at')
serializer = OrderSerializer(orders, many=True)
# Merge tracking details from SellerOrders
response_data = []
for order_data in serializer.data:
order_id = order_data['id']
seller_orders = SellerOrder.objects.filter(order_id__startswith=f"{order_id}-")
# Enrich with tracking details if available
order_data['items'] = []
for s_ord in seller_orders:
order_data['items'].append({
"product_title": s_ord.item,
"quantity": s_ord.quantity,
"unit_price": float(s_ord.total / s_ord.quantity),
"tracking_number": s_ord.tracking if s_ord.tracking != 'Pending' else None,
"carrier": s_ord.carrier if s_ord.carrier != 'Pending' else None,
"status": s_ord.status
})
# Aggregate status
if seller_orders.exists():
statuses = [o.status for o in seller_orders]
if 'Pending Acceptance' in statuses:
order_data['status'] = 'pending'
elif 'Ready to Ship' in statuses:
order_data['status'] = 'confirmed'
elif 'Shipped' in statuses:
order_data['status'] = 'shipped'
elif 'Delivered' in statuses:
order_data['status'] = 'delivered'
response_data.append(order_data)
return Response(response_data)
class OrderDetailView(APIView):
permission_classes = [permissions.IsAuthenticated]
def get(self, request, pk):
try:
order = Order.objects.get(id=pk, user=request.user)
except Order.DoesNotExist:
return Response({"error": "Order not found"}, status=status.HTTP_404_NOT_FOUND)
serializer = OrderSerializer(order)
order_data = serializer.data
seller_orders = SellerOrder.objects.filter(order_id__startswith=f"{pk}-")
order_data['items'] = []
for s_ord in seller_orders:
order_data['items'].append({
"product_title": s_ord.item,
"quantity": s_ord.quantity,
"unit_price": float(s_ord.total / s_ord.quantity),
"tracking_number": s_ord.tracking if s_ord.tracking != 'Pending' else None,
"carrier": s_ord.carrier if s_ord.carrier != 'Pending' else None,
"status": s_ord.status
})
return Response(order_data)