schon/core/serializers/simple.py
Egor fureunoir Gorbunov 3ec0991aa6 Add slug field to Product and update related functionalities
Introduce a unique, auto-generated slug field to the Product model, populated from category, brand, and name. Update core filters, serializers, sitemaps, and GraphQL object types to support the new slug functionality. Also, enforce HTTP-only cookies for session, CSRF, and language for improved security.
2025-04-30 16:31:54 +03:00

299 lines
6.9 KiB
Python

from contextlib import suppress
from typing import Optional
from rest_framework.fields import SerializerMethodField
from rest_framework.relations import PrimaryKeyRelatedField
from rest_framework.serializers import ModelSerializer
from core.models import (
Attribute,
AttributeGroup,
AttributeValue,
Brand,
Category,
Feedback,
Order,
OrderProduct,
Product,
ProductImage,
ProductTag,
PromoCode,
Promotion,
Stock,
Vendor,
Wishlist,
)
class AttributeGroupSimpleSerializer(ModelSerializer):
parent = PrimaryKeyRelatedField(read_only=True)
children = PrimaryKeyRelatedField(many=True, read_only=True)
class Meta:
model = AttributeGroup
fields = [
"uuid",
"name",
"parent",
"children",
]
class CategorySimpleSerializer(ModelSerializer):
children = SerializerMethodField()
image = SerializerMethodField()
class Meta:
model = Category
fields = [
"uuid",
"name",
"image",
"children",
]
def get_image(self, obj: Category) -> Optional[str]:
with suppress(ValueError):
return obj.image.url
return None
def get_children(self, obj) -> list[dict]:
request = self.context.get("request")
if request is not None and request.user.has_perm("view_category"):
children = obj.children.all()
else:
children = obj.children.filter(is_active=True)
if obj.children.exists():
return (
CategorySimpleSerializer(children, many=True, context=self.context).data
if obj.children.exists()
else []
)
else:
return []
class BrandSimpleSerializer(ModelSerializer):
small_logo = SerializerMethodField()
big_logo = SerializerMethodField()
class Meta:
model = Brand
fields = [
"uuid",
"name",
"small_logo",
"big_logo",
]
def get_small_logo(self, obj: Brand) -> Optional[str]:
with suppress(ValueError):
return obj.small_logo.url
return None
def get_big_logo(self, obj: Brand) -> Optional[str]:
with suppress(ValueError):
return obj.big_logo.url
return None
class ProductTagSimpleSerializer(ModelSerializer):
class Meta:
model = ProductTag
fields = [
"uuid",
"tag_name",
"name",
]
class ProductImageSimpleSerializer(ModelSerializer):
product = PrimaryKeyRelatedField(read_only=True)
class Meta:
model = ProductImage
fields = [
"uuid",
"alt",
"image",
"priority",
"product",
]
class AttributeSimpleSerializer(ModelSerializer):
group = AttributeGroupSimpleSerializer(read_only=True)
class Meta:
model = Attribute
fields = [
"uuid",
"name",
"value_type",
"group",
]
class AttributeValueSimpleSerializer(ModelSerializer):
attribute = AttributeSimpleSerializer(read_only=True)
product = PrimaryKeyRelatedField(read_only=True)
class Meta:
model = AttributeValue
fields = [
"uuid",
"value",
"attribute",
"product",
]
class ProductSimpleSerializer(ModelSerializer):
brand = BrandSimpleSerializer(read_only=True)
category = CategorySimpleSerializer(read_only=True)
tags = ProductTagSimpleSerializer(many=True, read_only=True)
images = ProductImageSimpleSerializer(many=True, read_only=True)
attributes = AttributeValueSimpleSerializer(many=True, read_only=True)
rating = SerializerMethodField()
price = SerializerMethodField()
quantity = SerializerMethodField()
feedbacks_count = SerializerMethodField()
class Meta:
model = Product
fields = [
"uuid",
"name",
"is_digital",
"slug",
"description",
"partnumber",
"brand",
"feedbacks_count",
"category",
"tags",
"images",
"attributes",
"rating",
"price",
"quantity",
]
def get_rating(self, obj: Product) -> float:
return obj.rating
def get_price(self, obj: Product) -> float:
return obj.price
def get_feedbacks_count(self, obj: Product) -> int:
return obj.feedbacks_count
def get_quantity(self, obj: Product) -> int:
return obj.quantity
class VendorSimpleSerializer(ModelSerializer):
class Meta:
model = Vendor
fields = [
"uuid",
"name",
]
class StockSimpleSerializer(ModelSerializer):
vendor = VendorSimpleSerializer(read_only=True)
product = ProductSimpleSerializer(read_only=True)
class Meta:
model = Stock
fields = [
"uuid",
"price",
"purchase_price",
"quantity",
"sku",
"vendor",
"product",
]
class PromoCodeSimpleSerializer(ModelSerializer):
class Meta:
model = PromoCode
fields = [
"uuid",
"code",
]
class PromotionSimpleSerializer(ModelSerializer):
products = ProductSimpleSerializer(many=True, read_only=True)
class Meta:
model = Promotion
fields = [
"uuid",
"name",
"discount_percent",
"products",
]
class WishlistSimpleSerializer(ModelSerializer):
user = PrimaryKeyRelatedField(read_only=True)
products = ProductSimpleSerializer(many=True, read_only=True)
class Meta:
model = Wishlist
fields = [
"uuid",
"user",
"products",
]
class FeedbackSimpleSerializer(ModelSerializer):
order_product = PrimaryKeyRelatedField(read_only=True)
class Meta:
model = Feedback
fields = [
"uuid",
"rating",
"order_product",
]
class OrderProductSimpleSerializer(ModelSerializer):
product = ProductSimpleSerializer(read_only=True)
class Meta:
model = OrderProduct
fields = [
"uuid",
"product",
"quantity",
"buy_price",
"status",
]
class OrderSimpleSerializer(ModelSerializer):
user = PrimaryKeyRelatedField(read_only=True)
promo_code = PromoCodeSimpleSerializer(read_only=True)
order_products = OrderProductSimpleSerializer(many=True, read_only=True)
class Meta:
model = Order
fields = [
"uuid",
"status",
"user",
"promo_code",
"order_products",
"buy_time",
]