web-dev-qa-db-fra.com

Code d'état HTTP pour les exceptions

j'ai un contrôleur SpringBoot et je veux renvoyer le code HTTP correct pour Exceptions. Ma question est donc la suivante: quel code HTTP est le meilleur pour Exception le "500" ou le "409"?

Ceci est mon code:

@PostMapping(value = {"", "/"})
public ResponseEntity<Response> create(@RequestBody StudioDto studioDto,
        ServletRequest servletRequest, ServletResponse servletResponse) {

    Response response = new Response();

    try {
        studioService.createStudio(studioDto);
        response.setMessage("The studio was create");
        response.setStatusCode(HttpServletResponse.SC_CREATED);

    } catch (Exception e) {
        response.setMessage("Op we have a little problem");
        response.setErrorMessage(e.getMessage());

        //Which one
        //this one 5xx
        response.setStatusCode(500);
        //Or this one 4xx
        response.setStatusCode(409);
    }

    return new ResponseEntity(response, response.getHttpStatus());
}
6
Carlos Mario

Ce n'est pas la façon recommandée de gérer les exceptions, vous devriez utiliser les conseils du contrôleur, vérifiez ceci link

Le code d'état est défini par le scénario spécifique. 500 signifie une erreur de serveur interne que j'utiliserais pour un problème dont la cause n'est pas spécifiée. Pour 409, il renvoie un conflit sur la ressource cible.

La demande n'a pas pu être complétée en raison d'un conflit avec le fichier .__ en cours. état de la ressource cible. Ce code est utilisé dans des situations où l'utilisateur pourrait peut-être résoudre le conflit et soumettre à nouveau le fichier demande

vous avez beaucoup d'autres codes d'état qui conviennent à différents cas, je dirais donc qu'aucun code d'état spécifique n'est la bonne réponse, vous pouvez vérifier ceci link pour plus d'informations

2
Amer Qarabsa

Todd a donné un excellent lien. C’est une meilleure façon de penser:

https://httpstatuses.com/

  • 1 × † informatif

  • 2x × Succès

  • 3 × ** redirection

  • 4 × × Erreur client * 400 Requête incorrecte * 401 Non autorisé ... * 405 Méthode non autorisée ...

  • 5 × † erreur de serveur * 500 erreur de serveur interne * 501 non implémentée * 502 passerelle incorrecte ...

En d'autres termes, chaque nombre majeur (200, 400, 500, etc.) est une catégorie . Vous pouvez "raffiner" le code d'erreur en choisissant une erreur spécifique dans la "catégorie".

A votre question initiale:

  • Si la demande Client est "incorrecte" (par exemple, nom d'utilisateur/mot de passe illégal), renvoyez un 4xx.

  • Si Server échoue (par exemple, vous ne pouvez pas lire la base de données), renvoyez un 5xx.

La liste "officielle" des codes d'erreur HTTP est la RFC 7231:

https://tools.ietf.org/html/rfc7231

4
paulsm4

Cela dépend du message que vous essayez de transmettre. Pensez au code d'état pour indiquer à l'appelant ce qu'il faut faire ensuite. S'il s'agit d'une erreur de serveur interne sur laquelle il est peu probable que l'utilisateur puisse faire quoi que ce soit, une erreur de 500 est appropriée.

Le serveur a rencontré une condition inattendue qui l'a empêché de répondre à la demande.

D'autre part, a 409 indique un conflit que l'utilisateur pourrait résoudre conceptuellement:

La demande n'a pas pu être complétée en raison d'un conflit avec l'état actuel de la ressource cible. Ce code est utilisé dans des situations où l'utilisateur peut éventuellement résoudre le conflit et soumettre à nouveau la demande.

La plupart des erreurs de niveau 400 indiquent que l'utilisateur pourrait, en théorie, les corriger et les soumettre à nouveau.

Personnellement, je vous conseillerais de capturer des exceptions plus précises et de déterminer le code d'état que chacun devrait renvoyer, car cela dépend vraiment de votre cas d'utilisation. À l'heure actuelle, vous attrapez Exception, et cela pourrait être à peu près tout, il est donc difficile de dire quel type de conseils vous devriez donner à l'appelant.

1
Todd

Les codes 5.XX signifient une erreur côté serveur et les codes 4.XXX, une erreur côté client.
Ici vous attrapez n'importe quelle exception:

 catch (Exception e) {
    response.setMessage("Op we have a little problem");
    response.setErrorMessage(e.getMessage());

    //Which one
    //this one 5xx
    response.setStatusCode(500);
    //Or this one 4xx
    response.setStatusCode(409);
}

Donc il est clairement impossible de savoir si le problème vient de la demande du client (paramètre incorrect, par exemple) ou d’une erreur du serveur (incohérence dans la base de données ou erreur de programmation, par exemple).

Pour pouvoir définir avec la précision 4.XXX ou 5.XXX, votre code peut s'appuyer sur des exceptions de base spécifiques telles que ClientErrorException et ServerErrorException.

Lancez l’un ou l’autre en fonction de la cause de l’erreur et vous pourrez alors compter sur eux pour définir le code de statut correct:

try {
    studioService.createStudio(studioDto);
    response.setMessage("The studio was create");
    response.setStatusCode(HttpServletResponse.SC_CREATED);
} 
 catch (ClientErrorException e) {
    response.setStatusCode(409);
}
catch (ServerErrorException e) {
    response.setStatusCode(500);
}

Une autre solution consiste à ajouter le champ de code d'état dans la classe de base des exceptions.
Vous pourriez si simplement écrire:

try {
    studioService.createStudio(studioDto);
    response.setMessage("The studio was create");
    response.setStatusCode(HttpServletResponse.SC_CREATED);

} 
 catch (MyRestException e) {
    response.setStatusCode(e.getStatusCode());
}

Ces exceptions personnalisées peuvent être levées directement de votre code lorsque vous détectez une erreur dans la demande du client (4.XXX).
De cette manière, vous pouvez considérer toutes les autres exceptions comme liées au traitement du serveur (5.XXX).
Un gestionnaire d’exception de printemps pourrait facilement effectuer cette tâche.

1
davidxxx