2023-05-28 15:06:50 +00:00
|
|
|
from typing import Any, Dict
|
|
|
|
|
2023-06-01 20:35:14 +00:00
|
|
|
from django.views.generic import (
|
|
|
|
TemplateView,
|
|
|
|
View
|
|
|
|
)
|
|
|
|
from django.shortcuts import render
|
|
|
|
from django.urls import reverse
|
|
|
|
from django.http import HttpResponseRedirect
|
2023-05-28 15:06:50 +00:00
|
|
|
from rest_framework.viewsets import ViewSet
|
|
|
|
from rest_framework.decorators import action
|
|
|
|
from rest_framework.response import Response
|
|
|
|
|
|
|
|
from store.cart import SessionCart
|
|
|
|
from store.serializers import (
|
2023-06-18 14:18:00 +00:00
|
|
|
CartSerializer,
|
2023-05-28 15:06:50 +00:00
|
|
|
CartProductAddSerializer
|
|
|
|
)
|
2023-06-01 20:35:14 +00:00
|
|
|
from store.forms import CustomerDataForm
|
|
|
|
from store.models import (
|
|
|
|
Order,
|
2023-06-18 14:18:00 +00:00
|
|
|
Product
|
2023-06-01 20:35:14 +00:00
|
|
|
)
|
2023-05-28 15:06:50 +00:00
|
|
|
|
|
|
|
|
|
|
|
class CartView(TemplateView):
|
|
|
|
"""
|
|
|
|
This view should simply render cart with initial data, it'll do that each refresh, for
|
|
|
|
making actions on cart (using jquery) we will use CartActionView, which will
|
|
|
|
be prepared to return JsonResponse.
|
|
|
|
"""
|
2023-05-25 01:16:01 +00:00
|
|
|
template_name = 'store/cart.html'
|
|
|
|
|
|
|
|
|
2023-05-28 15:06:50 +00:00
|
|
|
def get_context_data(self, **kwargs: Any) -> Dict[str, Any]:
|
|
|
|
context = super().get_context_data(**kwargs)
|
|
|
|
context["cart"] = SessionCart(self.request)
|
|
|
|
return context
|
|
|
|
|
|
|
|
|
|
|
|
class CartActionView(ViewSet):
|
|
|
|
|
2023-06-18 14:18:00 +00:00
|
|
|
# TODO - test this, currently not in use
|
2023-05-28 15:06:50 +00:00
|
|
|
@action(detail=False, methods=["get"], url_path="list-products")
|
|
|
|
def list_products(self, request):
|
|
|
|
# get cart items
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
items = cart.get_items()
|
2023-06-18 14:18:00 +00:00
|
|
|
serializer = CartSerializer(instance=items, many=True)
|
2023-05-28 16:35:08 +00:00
|
|
|
return Response(serializer.data)
|
2023-05-28 15:06:50 +00:00
|
|
|
|
|
|
|
@action(detail=False, methods=["post"])
|
|
|
|
def add_product(self, request):
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
serializer = CartProductAddSerializer(data=request.POST)
|
2023-05-28 16:35:08 +00:00
|
|
|
if not serializer.is_valid():
|
2023-05-28 15:06:50 +00:00
|
|
|
return Response(serializer.errors, status=400)
|
|
|
|
serializer.save(cart)
|
|
|
|
items = cart.get_items()
|
2023-06-18 14:18:00 +00:00
|
|
|
serializer = CartSerializer(instance=items, many=True)
|
2023-05-28 16:35:08 +00:00
|
|
|
return Response(serializer.data, status=201)
|
2023-05-28 15:06:50 +00:00
|
|
|
|
2023-05-28 16:35:08 +00:00
|
|
|
@action(detail=False, methods=["post"])
|
|
|
|
def remove_product(self, request):
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
product_id = request.POST.get("product_id")
|
2023-06-18 14:18:00 +00:00
|
|
|
try:
|
|
|
|
cart.remove_item(product_id)
|
|
|
|
except Product.DoesNotExist:
|
|
|
|
return Response({"error": "Product does not exist"}, status=400)
|
2023-05-28 16:35:08 +00:00
|
|
|
|
|
|
|
items = cart.get_items()
|
2023-06-18 14:18:00 +00:00
|
|
|
serializer = CartSerializer(instance=items, many=True)
|
2023-05-28 16:35:08 +00:00
|
|
|
return Response(serializer.data, status=201)
|
2023-06-01 20:35:14 +00:00
|
|
|
|
|
|
|
@action(detail=True, methods=["put"])
|
2023-06-08 17:49:19 +00:00
|
|
|
def update_product(self, request, pk):
|
2023-06-01 20:35:14 +00:00
|
|
|
cart = SessionCart(self.request)
|
2023-06-18 14:18:00 +00:00
|
|
|
try:
|
|
|
|
cart.update_item_quantity(pk, int(request.data["quantity"]))
|
|
|
|
except Product.DoesNotExist:
|
|
|
|
return Response({"error": "Product does not exist"}, status=404)
|
2023-06-01 20:35:14 +00:00
|
|
|
items = cart.get_items()
|
2023-06-18 14:18:00 +00:00
|
|
|
serializer = CartSerializer(instance=items, many=True)
|
2023-06-01 20:35:14 +00:00
|
|
|
return Response(serializer.data, status=201)
|
|
|
|
|
|
|
|
|
|
|
|
class OrderView(View):
|
|
|
|
template_name = "store/order.html"
|
|
|
|
|
|
|
|
def get_context_data(self, **kwargs: Any) -> Dict[str, Any]:
|
|
|
|
context = {}
|
|
|
|
context["form"] = CustomerDataForm()
|
|
|
|
return context
|
|
|
|
|
|
|
|
def get(self, request, *args, **kwargs):
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
if cart.is_empty():
|
|
|
|
# TODO - messages
|
|
|
|
return HttpResponseRedirect(reverse("cart"))
|
|
|
|
return render(request, self.template_name, self.get_context_data())
|
|
|
|
|
|
|
|
def post(self, request, *args, **kwargs):
|
|
|
|
# TODO - messages
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
if cart.is_empty():
|
|
|
|
return HttpResponseRedirect(reverse("cart"))
|
|
|
|
form = CustomerDataForm(request.POST)
|
|
|
|
if not form.is_valid():
|
|
|
|
context = self.get_context_data()
|
|
|
|
context["form"] = form
|
|
|
|
return render(request, self.template_name, context)
|
2023-06-18 14:18:00 +00:00
|
|
|
customer_data = form.data
|
|
|
|
# TODO - add encryption
|
|
|
|
request.session["customer_data"] = customer_data
|
2023-06-01 20:35:14 +00:00
|
|
|
return HttpResponseRedirect(reverse("order-confirm"))
|
|
|
|
|
|
|
|
|
|
|
|
class OrderConfirmView(View):
|
|
|
|
template_name = "store/order_confirm.html"
|
|
|
|
|
|
|
|
def get_context_data(self, **kwargs: Any) -> Dict[str, Any]:
|
2023-06-18 14:18:00 +00:00
|
|
|
customer_data = self.request.session["customer_data"]
|
2023-06-01 20:35:14 +00:00
|
|
|
return {
|
|
|
|
"cart": SessionCart(self.request),
|
|
|
|
"customer_data": customer_data
|
|
|
|
}
|
|
|
|
|
|
|
|
def get(self, request, *args, **kwargs):
|
|
|
|
cart = SessionCart(self.request)
|
|
|
|
if cart.is_empty():
|
|
|
|
# TODO - messages
|
|
|
|
return HttpResponseRedirect(reverse("cart"))
|
|
|
|
return render(request, self.template_name, self.get_context_data())
|
|
|
|
|
|
|
|
def post(self, request):
|
2023-06-18 14:18:00 +00:00
|
|
|
customer_data = request.session["customer_data"]
|
2023-06-01 20:35:14 +00:00
|
|
|
cart = SessionCart(self.request)
|
2023-06-18 14:18:00 +00:00
|
|
|
Order.objects.create_from_cart(
|
|
|
|
cart.get_items(),
|
|
|
|
None, customer_data
|
2023-06-01 20:35:14 +00:00
|
|
|
)
|
2023-06-18 14:18:00 +00:00
|
|
|
request.session.pop("customer_data")
|
2023-06-07 23:39:06 +00:00
|
|
|
cart.clear()
|
2023-06-01 20:35:14 +00:00
|
|
|
# TODO - messages
|
2023-06-07 23:09:51 +00:00
|
|
|
return HttpResponseRedirect(reverse("cart"))
|