diff --git a/api_doc.txt b/api_doc.txt index fb0d396..556e2b8 100644 --- a/api_doc.txt +++ b/api_doc.txt @@ -45,6 +45,13 @@ Inventory Products Endpoints: - Request Body: nil - Response: nil +Note: This search functionality works when postgres database is used +5. GET /api/inventory/products/search?q= + - Description: Search for products by the specified field + - Request Body: nil + - Response: list of products + - Search From: title, description + Inventory Orders Endpoints: @@ -66,6 +73,7 @@ Inventory Orders Endpoints: - Description: List orders - Request Body: nil - Response: list of orders + - Filters: status, date_from, date_to 3. PUT /api/inventory/orders/:id/status/ - Description: Update order status by an admin user diff --git a/drugstoc_inventory/settings.py b/drugstoc_inventory/settings.py index eab89b1..2cb39e3 100644 --- a/drugstoc_inventory/settings.py +++ b/drugstoc_inventory/settings.py @@ -34,6 +34,7 @@ 'rest_framework', 'rest_framework_simplejwt', 'rest_framework_simplejwt.token_blacklist', + 'django_filters', #internal apps "users", "inventory" diff --git a/inventory/views.py b/inventory/views.py index fc22bba..eef3988 100644 --- a/inventory/views.py +++ b/inventory/views.py @@ -1,11 +1,14 @@ # views.py import logging from django.contrib.postgres.search import SearchQuery, SearchRank +from django_filters import rest_framework as filters + from rest_framework import status, permissions from rest_framework.response import Response from rest_framework.views import APIView from django.shortcuts import get_object_or_404 from django.http import Http404 +from rest_framework.pagination import PageNumberPagination from django.db.models import Sum, F from datetime import datetime, timedelta from .models import Product, Order, OrderItem @@ -24,8 +27,13 @@ class InventoryProductList(APIView): def get(self, request): logger.info(f"User {request.user.id} requested product list") products = Product.objects.all() - serializer = ProductSerializer(products, many=True) - return Response(serializer.data) + + # Apply pagination + paginator = PageNumberPagination() + paginated_products = paginator.paginate_queryset(products, request) + + serializer = ProductSerializer(paginated_products, many=True) + return paginator.get_paginated_response(serializer.data) class InventoryProductCreate(APIView): permission_classes = [permissions.IsAuthenticated, IsAdminOrReadOnly] @@ -73,6 +81,17 @@ def delete(self, request, pk): return Response(status=status.HTTP_204_NO_CONTENT) +class OrderFilter(filters.FilterSet): + status = filters.CharFilter(field_name='status', lookup_expr='iexact') + date_from = filters.DateFilter(field_name='created_at', lookup_expr='gte') + date_to = filters.DateFilter(field_name='created_at', lookup_expr='lte') + + class Meta: + model = Order + fields = ['status', 'created_at'] + + + class OrderListCreate(APIView): permission_classes = [permissions.IsAuthenticated] authentication_classes = [CustomJWTAuthentication] @@ -80,6 +99,12 @@ class OrderListCreate(APIView): def get(self, request): logger.info(f"User {request.user.id} requested their order list") orders = Order.objects.filter(owner=request.user) + + filterset = OrderFilter(request.GET, queryset=orders) + if not filterset.is_valid(): + return Response(filterset.errors, status=status.HTTP_400_BAD_REQUEST) + + orders = filterset.qs serializer = OrderSerializer(orders, many=True) return Response(serializer.data) diff --git a/requirements.txt b/requirements.txt index 7b5c21d..2aa8589 100644 --- a/requirements.txt +++ b/requirements.txt @@ -5,6 +5,8 @@ Pillow==10.3.0 pytest-django==4.8.0 django-redis==5.4.0 +django_filter==24.2 + whitenoise # https://github.com/evansd/whitenoise redis # https://github.com/redis/redis-py hiredis # https://github.com/redis/hiredis-py