Add product review model, serializer, and API endpoint

Introduces a Review model for product reviews, including rating and comment fields. Adds a public serializer and a ModelViewSet for reviews with search and ordering capabilities. Also updates the frontend API client to use the correct token refresh endpoint and improves FormData handling.
This commit is contained in:
2026-01-14 00:10:46 +01:00
parent 2213e115c6
commit 98426f8b05
4 changed files with 47 additions and 6 deletions

View File

@@ -616,4 +616,22 @@ class Invoice(models.Model):
# Save directly to FileField
self.pdf_file.save(f"{self.invoice_number}.pdf", ContentFile(pdf_bytes))
self.save()
self.save()
class Review(models.Model):
product = models.ForeignKey(Product, related_name="reviews", on_delete=models.CASCADE)
user = models.ForeignKey(
settings.AUTH_USER_MODEL, on_delete=models.CASCADE, related_name="reviews"
)
rating = models.PositiveIntegerField(
validators=[MinValueValidator(1), MaxValueValidator(5)]
)
comment = models.TextField(blank=True)
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
def __str__(self):
return f"Review for {self.product.name} by {self.user.username}"

View File

@@ -2,7 +2,7 @@ from rest_framework import serializers
from thirdparty.stripe.client import StripeClient
from .models import Refund, Order, Invoice
from .models import Refund, Order, Invoice, Review
class RefundCreatePublicSerializer(serializers.Serializer):
@@ -465,3 +465,9 @@ class OrderReadSerializer(serializers.ModelSerializer):
return list(obj.discount.values_list("code", flat=True))
class ReviewSerializerPublic(serializers.Serializer):
class Meta:
model = Review
fields = "__all__"

View File

@@ -4,8 +4,8 @@ from rest_framework.response import Response
from rest_framework import status
import base64
from .models import Refund
from .serializers import RefundCreatePublicSerializer
from .models import Refund, Review
from .serializers import RefundCreatePublicSerializer, ReviewSerializerPublic
from django.db import transaction
@@ -414,4 +414,16 @@ class RefundPublicView(APIView):
"base64": pdf_b64,
},
}
return Response(resp, status=status.HTTP_201_CREATED)
return Response(resp, status=status.HTTP_201_CREATED)
class ReviewPublicViewSet(viewsets.ModelViewSet):
queryset = Review.objects.all()
serializer_class = ReviewSerializerPublic
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
filter_backends = [filters.SearchFilter, filters.OrderingFilter]
search_fields = ["product__name", "user__username", "comment"]
ordering_fields = ["rating", "created_at"]
ordering = ["-created_at"]