В уроке 7 по созданию API на Django REST Framework, мы рассмотрим использование прав доступа пользователя на возможности взаимодействия с API.
В предыдущем уроке мы рассмотрели миксины на основе классов: Django REST Framework создание API: Урок 6, миксины для представлений
В этом уроке мы приступим к правам доступа, поэтому я верну все представления по отдельности для примера:
modules/blog/views/articles.py
from modules.blog.models import Article
from modules.blog.serializers import ArticleSerializer
from rest_framework import generics
from django.template.defaultfilters import slugify
class ArticleRetrieveAPIView(generics.RetrieveAPIView):
"""
Представление для получения одной статьи (GET)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
lookup_field = 'slug'
class ArticleListAPIView(generics.ListAPIView):
"""
Представление для получения списка статей (GET)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
class ArticleCreateAPIView(generics.CreateAPIView):
"""
Представление для создания списка статей (POST)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
def perform_create(self, serializer):
# Если не задан слаг, генерируем его из заголовка
slug = serializer.validated_data.get('slug')
if slug is None:
slug = slugify(serializer.validated_data.get('title'))
serializer.save(slug=slug)
print(serializer.validated_data)
return super().perform_create(serializer)
class ArticleUpdateAPIView(generics.UpdateAPIView):
"""
Представление для обновления статей (PUT)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
lookup_field = 'slug'
class ArticleDestroyAPIView(generics.DestroyAPIView):
"""
Представление для удаления статей (DELETE)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
lookup_field = 'slug'
Необязательно для тех, кто делает все в файле views.py.
Добавлю импорты в __init__.py:
from modules.blog.views.articles import *
__all__ = '__all__'
И добавлю обработку представлений в urls.py
from django.urls import path
from modules.blog import views
urlpatterns = [
path('articles/', views.ArticleListAPIView.as_view(), name='api_articles_list'),
path('articles/create/', views.ArticleCreateAPIView.as_view(), name='api_articles_create'),
path('articles/<str:slug>/', views.ArticleRetrieveAPIView.as_view(), name='api_articles_detail'),
path('articles/<str:slug>/update/', views.ArticleUpdateAPIView.as_view(), name='api_articles_update'),
path('articles/<str:slug>/delete/', views.ArticleDestroyAPIView.as_view(), name='api_articles_delete'),
]
Отлично, теперь можно приступать к рассмотрению прав доступа и сессий.
Существующие в DRF права доступа:
AllowAny
- независимо от того, что аутентифицирован, или прошел ли пользователь проверку подлинности.IsAuthenticated
- данный класс, позволяет работать с апи авторизированным пользователям.IsAdminUser
- этот класс позволяет работать только тем пользователям, у кого user.staff = True, т.е админ.IsAuthenticatedOrReadOnly
- если пользователь аутентифицирован, то он может изменять, работать с апи, а если не аутентифицирован, то может только просматривать.DjangoModelPermissions
- этот класс разрешений связан с разрешениями стандартной модели Django.
Рассмотрим базовые права доступа на примере ArticleCreateAPIView
:
modules/blog/views/articles.py
from modules.blog.models import Article
from modules.blog.serializers import ArticleSerializer
from rest_framework import generics, permissions
from django.template.defaultfilters import slugify
class ArticleCreateAPIView(generics.CreateAPIView):
"""
Представление для создания списка статей (POST)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
permission_classes = [permissions.IsAuthenticated]
def perform_create(self, serializer):
# Если не задан слаг, генерируем его из заголовка
slug = serializer.validated_data.get('slug')
if slug is None:
slug = slugify(serializer.validated_data.get('title'))
serializer.save(slug=slug)
print(serializer.validated_data)
return super().perform_create(serializer)
Пояснение:
- Из rest_framework импортировал permissions
- В список
permission_classes
, добавилpermissions.IsAuthenticated
- В данном случае, мы сможем создавать статьи, если мы авторизованы.
Поэтому давайте перейдем с гостя и с авторизованного пользователя на страницу: http://127.0.0.1:8000/api/articles/create/
В первом случае я авторизованный пользователей:

Во втором случае я не авторизован:

Ну и ещё один пример, если мы будем администратором и простым пользователем.
modules/blog/views/articles.py
class ArticleListAPIView(generics.ListAPIView):
"""
Представление для получения списка статей (GET)
"""
queryset = Article.objects.all()
serializer_class = ArticleSerializer
permission_classes = [permissions.IsAdminUser]
Обратимся на страницу со списком статей: http://127.0.0.1:8000/api/articles/
С аккаунта администратора:

С аккаунта пользователя:

В этом уроке мы бегло рассмотрели базовые примеры использования прав доступа из DRF, в следующем уроке мы рассмотрим деление прав доступа по группам, а также будем плавно переходить к авторизации по токенам.