Project

General

Profile

Support #69085

Sur un POST d'API, lever une erreur quand un slash final manque au lieu de rediriger ?

Added by Valentin Deniaud about 2 years ago. Updated about 2 years ago.

Status:
Fermé
Priority:
Normal
Assignee:
-
Category:
-
Target version:
-
Start date:
14 September 2022
Due date:
% Done:

0%

Estimated time:
Patch proposed:
No
Planning:
No
Club:
No

Description

La plupart de nos API sur les briques Django prennent un / final.

On a le setting Django APPEND_SLASH à True (valeur par défaut, https://docs.djangoproject.com/en/4.1/ref/settings/#append-slash), qui fait que si on appelle une URL en oubliant le / final, il y a redirection vers la bonne URL avec le /.

C'est très bien en front ou pour les API qui s'appellent via GET.

Par contre en POST/PATCH/PUT, la redirection se fait et on perd les données, donc on se retrouve à avoir un appel qui semble fonctionner et en fait pas du tout (voir ticket lié).

Est-ce qu'on écrirait pas un bout de middleware qui si le chemin commence par api, renvoie une erreur JSON informant qu'il manque le slash final ?


Related issues

Related to Chrono - Autre #67478: Un PATCH sur /api/agenda/SLUG-DE-LAGENDA/event/SLUG-DE-LEVENEMENT ne retourne pas d'erreurFermé19 July 2022

Actions
Related to Hobo - Développement #69409: ajout d'un middleware pour désactiver append_slash sur un POST d'APIFermé21 September 2022

Actions

History

#1

Updated by Valentin Deniaud about 2 years ago

  • Related to Autre #67478: Un PATCH sur /api/agenda/SLUG-DE-LAGENDA/event/SLUG-DE-LEVENEMENT ne retourne pas d'erreur added
#2

Updated by Paul Marillonnet about 2 years ago

(À noter que si on estime que c’est pas grave que l’ajout automatique du slash final n’ait pas lieu sur toutes les api quel que soit le verbe http, et que si le problème peut attendre qu’on ait django 3.2 partout, alors on peut décorer les vues d’api de façon à les exclure de la conf globale APPEND_SLASH : https://docs.djangoproject.com/en/3.2/topics/http/decorators/#django.views.decorators.common.no_append_slash)

#3

Updated by Paul Marillonnet about 2 years ago

Paul Marillonnet a écrit :

(À noter que si on estime que c’est pas grave que l’ajout automatique du slash final n’ait pas lieu sur toutes les api quel que soit le verbe http, et que si le problème peut attendre qu’on ait django 3.2 partout, alors on peut décorer les vues d’api de façon à les exclure de la conf globale APPEND_SLASH : https://docs.djangoproject.com/en/3.2/topics/http/decorators/#django.views.decorators.common.no_append_slash)

Mais bien sûr ça va péter des appels GET existants, on oublie.

#4

Updated by Benjamin Dauvergne about 2 years ago

Paul Marillonnet a écrit :

(À noter que si on estime que c’est pas grave que l’ajout automatique du slash final n’ait pas lieu sur toutes les api quel que soit le verbe http, et que si le problème peut attendre qu’on ait django 3.2 partout, alors on peut décorer les vues d’api de façon à les exclure de la conf globale APPEND_SLASH : https://docs.djangoproject.com/en/3.2/topics/http/decorators/#django.views.decorators.common.no_append_slash)

C'est tout simplement plus simple de dériver de CommonMiddleware:

from django.middleware.common import CommonMiddleware

class APICommonMiddleware(BaseCommonMiddleware):
    def process_request(self, request):
        response = super().process_request(request)
        if response and self.should_redirect_with_slash(request) and request.path_info.startswith('/api/') and request.method != 'GET':
            return JsonResponse({'err': 1, 'err_desc': 'add a slash'}, status=404)
        return response

    def process_response(self, request, response):
        response_is_404 = (response.status_code == 404)
        response = super().process_response(request, response)
        if response_is_404 and isinstance(response, self.response_redirect_class) and self.should_redirect_with_slash(request) and request.path_info.startswith('/api/') and request.method != 'GET':
            return JsonResponse({'err': 1, 'err_desc': 'add a slash'}, status=404)
        return response
#5

Updated by Paul Marillonnet about 2 years ago

Benjamin Dauvergne a écrit :

C'est tout simplement plus simple de dériver de CommonMiddleware:

Oui j’étais juste pas fan du traitement du slash final manquant qui varie selon le verbe qu’on envoie, mais comme il y a forcément ici et là des appels GET en place avec le slash manquant, on n’a pas tellement le choix. Pas de meilleure solution à proposer que celle de Valentin et toi, elle me va si elle peut prévenir les appels qui font semblant de fonctionner.

#6

Updated by Valentin Deniaud about 2 years ago

  • Related to Développement #69409: ajout d'un middleware pour désactiver append_slash sur un POST d'API added
#7

Updated by Valentin Deniaud about 2 years ago

  • Status changed from Nouveau to Fermé

Merci pour les avis, j'ai ouvert le ticket technique pour mettre ça en place.

Also available in: Atom PDF