Должны ли классы аутентификации и классы разрешений в представлениях Django REST Framework определяться с помощью списков или кортежей?

Я пытаюсь понять, как лучше всего устанавливать классы аутентификации и классы разрешений в APIView Django REST Framework. В частности, я видел, как для определения этих атрибутов используются как кортежи, так и списки:

Использование кортежа:

class Home(APIView):
    authentication_classes = (JWTAuthentication,)
    permission_classes = (permissions.IsAuthenticated,)

Использование списка:

class Home(APIView):
    authentication_classes = [JWTAuthentication]
    permission_classes = [permissions.IsAuthenticated]

Кажется, оба подхода работают правильно, но я не уверен, есть ли какие-то конкретные причины предпочитать один другому. Должен ли я использовать список или кортеж в этом сценарии? Есть ли какие-либо последствия для использования одного над другим с точки зрения производительности, читаемости или следования лучшим практикам Django REST Framework?

Я пробовал использовать как кортежи, так и списки для классов аутентификации и классов разрешений в APIView Django REST Framework. Оба работают нормально, но я не уверен, какой из них лучше или рекомендуется. Я ожидал найти четкие указания по этому поводу.

Этот вопрос похож на: В чем разница между списками и кортежами?. Если вы считаете, что это другое, отредактируйте вопрос, поясните, чем он отличается и/или как ответы на этот вопрос не помогают решить вашу проблему.

Lord Elrond 01.09.2024 22:16

Кортежи неизменяемы и более эффективны; но в этом контексте не имеет значения, какой из них вы используете.

Lord Elrond 01.09.2024 22:18
Почему в Python есть оператор "pass"?
Почему в Python есть оператор "pass"?
Оператор pass в Python - это простая концепция, которую могут быстро освоить даже новички без опыта программирования.
Некоторые методы, о которых вы не знали, что они существуют в Python
Некоторые методы, о которых вы не знали, что они существуют в Python
Python - самый известный и самый простой в изучении язык в наши дни. Имея широкий спектр применения в области машинного обучения, Data Science,...
Основы Python Часть I
Основы Python Часть I
Вы когда-нибудь задумывались, почему в программах на Python вы видите приведенный ниже код?
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
Алиса и Боб имеют неориентированный граф из n узлов и трех типов ребер:
Оптимизация кода с помощью тернарного оператора Python
Оптимизация кода с помощью тернарного оператора Python
И последнее, что мы хотели бы показать вам, прежде чем двигаться дальше, это
Советы по эффективной веб-разработке с помощью Python
Советы по эффективной веб-разработке с помощью Python
Как веб-разработчик, Python может стать мощным инструментом для создания эффективных и масштабируемых веб-приложений.
1
2
51
3
Перейти к ответу Данный вопрос помечен как решенный

Ответы 3

Ответ принят как подходящий

Оба работают одинаково. В документации Django REST Framework, кажется, отдаются предпочтение спискам, так что, возможно, стоит использовать списки.

class ListUsers(APIView):
    authentication_classes = [authentication.TokenAuthentication]
    permission_classes = [permissions.IsAdminUser]

Сначала я объясню процесс аутентификации в DRF.

class APIView(View):
    def initialize_request(self, request, *args, **kwargs):
        """
        Returns the initial request object.
        """
        parser_context = self.get_parser_context(request)

        return Request(
            request,
            parsers=self.get_parsers(),
            authenticators=self.get_authenticators(),
            negotiator=self.get_content_negotiator(),
            parser_context=parser_context
        )

Функция, которая фактически выполняет аутентификацию в DRF, — это функция Perform_authentication, но перед этим, когда метод Initialize_request создает объект запроса, он вызывает метод get_authenticators и передает его в аргумент.

class APIView(View):
    ...
    def get_authenticators(self):
        """
        Instantiates and returns the list of authenticators that this view can use.
        """
        return [auth() for auth in self.authentication_classes]
    ...

Здесь функция get_authenticators повторяет переменную аутентификации_classes, определенную в представлении, созданном пользователями, для создания и возврата каждого объекта класса аутентификации.

В этом процессе используется переменная Authentication_classes, определенная спрашивающим.

И, как вы можете видеть из приведенного выше кода, это должен быть повторяемый объект, поскольку он используется в операторе for. Вот почему допускаются аранжировки и кортежи.

Проверка разрешений такая же.

class APIView(View):
    def dispatch(self, request, *args, **kwargs):
        ...
        try:
            self.initial(request, *args, **kwargs)

    def initial(self, request, *args, **kwargs):
        ...
        self.check_permissions(request)
        ...

    def check_permissions(self, request):
        for permission in self.get_permissions():
            if not permission.has_permission(request, self):
        ...

    def get_permissions(self):
        """
        Instantiates and returns the list of permissions that this view requires.
        """
        return [permission() for permission in self.permission_classes]

Процесс проверки разрешений в DRF APIView аналогичен описанному выше.

Значение Permissions_classes, установленное пользователем, используется в методе get_permissions и выполняет тот же процесс аутентификации, что и ранее.

То есть, поскольку классы разрешений или классы аутентификации должны использоваться в повторениях, вам придется использовать массив или кортеж этих проблемных типов данных.

Причина, по которой DRF реализовал описанную выше логику для разрешений и аутентификации, заключается в том, чтобы разрешить использование множественной аутентификации и разрешений.

Хороший ответ, но я не думаю, что вам нужны такие подробные объяснения.

Luke L 02.09.2024 00:37

«почему Django реализовал» — Django ничего из этого не реализует. DRF, совершенно отдельный проект, делает это.

AKX 02.09.2024 07:48

Сразу к делу: работают и tuple, и list. По сути, если вы хотите изменить переменную, используйте списки. Если вы специально не хотите и не хотите, чтобы переменную кто-то менял, то используйте кортежи. Здесь речь идет просто о проблеме неизменности и изменчивости.

Другие вопросы по теме