Django Rest Framework Views - Panduan Lengkap
1. Function Based Views
Dasar API View
# views.py
from rest_framework.decorators import api_view
from rest_framework.response import Response
@api_view(['GET', 'POST'])
def product_list(request):
if request.method == 'GET':
products = Product.objects.all()
serializer = ProductSerializer(products, many=True)
return Response(serializer.data)
elif request.method == 'POST':
serializer = ProductSerializer(data=request.data)
if serializer.is_valid():
serializer.save()
return Response(serializer.data, status=201)
return Response(serializer.errors, status=400)
API View dengan Detail
@api_view(['GET', 'PUT', 'DELETE'])
def product_detail(request, pk):
try:
product = Product.objects.get(pk=pk)
except Product.DoesNotExist:
return Response(status=404)
if request.method == 'GET':
serializer = ProductSerializer(product)
return Response(serializer.data)
elif request.method == 'PUT':
serializer = ProductSerializer(product, data=request.data)
if serializer.is_valid():
serializer.save()
return Response(serializer.data)
return Response(serializer.errors, status=400)
elif request.method == 'DELETE':
product.delete()
return Response(status=204)
2. Class Based Views
Generic API Views
from rest_framework import generics
class ProductList(generics.ListCreateAPIView):
queryset = Product.objects.all()
serializer_class = ProductSerializer
class ProductDetail(generics.RetrieveUpdateDestroyAPIView):
queryset = Product.objects.all()
serializer_class = ProductSerializer
ViewSet
from rest_framework import viewsets
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
3. Permissions
Penggunaan Permission
from rest_framework.permissions import IsAuthenticated, IsAdminUser
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
permission_classes = [IsAuthenticated]
Custom Permission
from rest_framework import permissions
class IsOwnerOrReadOnly(permissions.BasePermission):
def has_object_permission(self, request, view, obj):
if request.method in permissions.SAFE_METHODS:
return True
return obj.owner == request.user
4. Filtering dan Searching
Filter Backend
from rest_framework import filters
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
filter_backends = [filters.SearchFilter, filters.OrderingFilter]
search_fields = ['name', 'description']
ordering_fields = ['price', 'created_at']
Custom Filtering
class ProductViewSet(viewsets.ModelViewSet):
serializer_class = ProductSerializer
def get_queryset(self):
queryset = Product.objects.all()
category = self.request.query_params.get('category', None)
if category is not None:
queryset = queryset.filter(category=category)
return queryset
5. Pagination
Setting Pagination
from rest_framework.pagination import PageNumberPagination
class StandardResultsSetPagination(PageNumberPagination):
page_size = 10
page_size_query_param = 'page_size'
max_page_size = 100
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
pagination_class = StandardResultsSetPagination
6. Authentication
Token Authentication
from rest_framework.authtoken.views import obtain_auth_token
from rest_framework.authentication import TokenAuthentication
# urls.py
urlpatterns = [
path('api-token-auth/', obtain_auth_token),
]
# views.py
class ProductViewSet(viewsets.ModelViewSet):
authentication_classes = [TokenAuthentication]
permission_classes = [IsAuthenticated]
7. Tips dan Trik
Overriding Methods
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
def perform_create(self, serializer):
serializer.save(owner=self.request.user)
def get_serializer_context(self):
context = super().get_serializer_context()
context['user'] = self.request.user
return context
Custom Actions
from rest_framework.decorators import action
class ProductViewSet(viewsets.ModelViewSet):
queryset = Product.objects.all()
serializer_class = ProductSerializer
@action(detail=True, methods=['post'])
def mark_featured(self, request, pk=None):
product = self.get_object()
product.is_featured = True
product.save()
return Response({'status': 'produk ditandai sebagai unggulan'})
Error Handling
from rest_framework.exceptions import ValidationError
class ProductViewSet(viewsets.ModelViewSet):
def create(self, request, *args, **kwargs):
try:
return super().create(request, *args, **kwargs)
except ValidationError as e:
return Response({
'error': 'Terjadi kesalahan validasi',
'details': str(e)
}, status=400)