Обзор DRF, установка, настройка проекта, первый сериализатор
DRF превращает Django в мощный инструмент для создания REST API, предоставляя готовые решения для сериализации, аутентификации, прав доступа и многих других задач.
REST (Representational State Transfer) — архитектурный стиль для распределённых систем. REST API использует HTTP-методы для операций с ресурсами:
Django REST Framework (DRF) — это мощный и гибкий фреймворк для создания веб-API на основе Django. Он предоставляет:
pip install djangorestframeworkДобавьте в settings.py:
INSTALLED_APPS = [
# ...
'rest_framework',
]
# Настройки DRF (опционально)
REST_FRAMEWORK = {
'DEFAULT_PERMISSION_CLASSES': [
'rest_framework.permissions.IsAuthenticated',
],
'DEFAULT_AUTHENTICATION_CLASSES': [
'rest_framework.authentication.SessionAuthentication',
'rest_framework.authentication.TokenAuthentication',
],
'PAGE_SIZE': 20,
}Создадим простую модель для примера:
# models.py
from django.db import models
from django.contrib.auth.models import User
class Article(models.Model):
title = models.CharField(max_length=200)
content = models.TextField()
author = models.ForeignKey(User, on_delete=models.CASCADE, related_name='articles')
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
class Meta:
ordering = ['-created_at']
def __str__(self):
return self.titleСериализатор преобразует модель в JSON и обратно:
# serializers.py
from rest_framework import serializers
from .models import Article
class ArticleSerializer(serializers.ModelSerializer):
"""Сериализатор для модели Article"""
# Поле author будет представлено как вложенный объект
author_name = serializers.CharField(source='author.username', read_only=True)
class Meta:
model = Article
fields = ['id', 'title', 'content', 'author', 'author_name', 'created_at', 'updated_at']
read_only_fields = ['created_at', 'updated_at']Ключевые моменты:
ModelSerializer автоматически создаёт поля на основе моделиsource указывает, откуда брать значение для поляread_only=True означает, что поле только для чтения (не принимается в запросе)fields = '__all__' включает все поля моделиСоздадим view для списка статей и отдельной статьи:
# views.py
from rest_framework.decorators import api_view
from rest_framework.response import Response
from rest_framework import status
from .models import Article
from .serializers import ArticleSerializer
@api_view(['GET', 'POST'])
def article_list(request):
"""
Список всех статей или создание новой.
GET — получить список, POST — создать статью.
"""
if request.method == 'GET':
articles = Article.objects.all()
serializer = ArticleSerializer(articles, many=True)
return Response(serializer.data)
elif request.method == 'POST':
serializer = ArticleSerializer(data=request.data)
if serializer.is_valid():
serializer.save(author=request.user)
return Response(serializer.data, status=status.HTTP_201_CREATED)
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
@api_view(['GET', 'PUT', 'DELETE'])
def article_detail(request, pk):
"""
Получение, обновление или удаление статьи по ID.
"""
try:
article = Article.objects.get(pk=pk)
except Article.DoesNotExist:
return Response({'error': 'Статья не найдена'}, status=status.HTTP_404_NOT_FOUND)
if request.method == 'GET':
serializer = ArticleSerializer(article)
return Response(serializer.data)
elif request.method == 'PUT':
serializer = ArticleSerializer(article, data=request.data)
if serializer.is_valid():
serializer.save()
return Response(serializer.data)
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
elif request.method == 'DELETE':
article.delete()
return Response(status=status.HTTP_204_NO_CONTENT)# urls.py
from django.urls import path
from . import views
urlpatterns = [
path('articles/', views.article_list, name='article-list'),
path('articles/<int:pk>/', views.article_detail, name='article-detail'),
]DRF предоставляет Browsable API — веб-интерфейс для тестирования:
python manage.py runserverhttp://127.0.0.1:8000/articles/Пример запроса через curl:
# Получить список статей
curl http://127.0.0.1:8000/articles/
# Создать статью (нужна аутентификация)
curl -X POST http://127.0.0.1:8000/articles/ \
-H "Authorization: Token YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{"title": "Моя статья", "content": "Текст статьи"}'DRF предоставляет удобные константы:
from rest_framework import status
# Успешные
status.HTTP_200_OK # 200
status.HTTP_201_CREATED # 201
status.HTTP_204_NO_CONTENT # 204
# Ошибки клиента
status.HTTP_400_BAD_REQUEST # 400
status.HTTP_401_UNAUTHORIZED # 401
status.HTTP_403_FORBIDDEN # 403
status.HTTP_404_NOT_FOUND # 404
# Ошибки сервера
status.HTTP_500_INTERNAL_SERVER_ERROR # 500DRF использует Response вместо HttpResponse:
from rest_framework.response import Response
# Правильно в DRF
return Response(data, status=201)
# Не используйте в DRF
# from django.http import HttpResponse
# return HttpResponse(data)Response автоматически рендерит данные в нужный формат (JSON, HTML и т.д.) в зависимости от заголовков запроса.
В этой теме вы познакомились с основами DRF:
@api_viewВ следующих темах вы узнаете:
Вопросы ещё не добавлены
Вопросы для этой подтемы ещё не добавлены.