2012-12-19 3 views
20

Je travaille sur un projet et ai beaucoup compté sur l'API web pour toutes mes opérations côté client, que ce soit la mise à jour des détails du compte, de nouveaux détails, tout ce qui a été fait avec ASP.NET Web Api et Backbone.jsMeilleure pratique: comment gérer les erreurs et les exceptions dans les contrôleurs d'API Web?

Scène actuelle:

Dans le schéma actuel des choses, je renvoie une valeur booléenne de mes contrôleurs api web, pour indiquer si l'opération était la réussite ou non.

Exemple:

[ActionName("UpdateAccountDetails")] 
public bool PostAccountDetails(SomeModel model) 
{ 
    bool updateStatus = _customService.UpdateAccountDetails(model); 
    return updateStatus; 
} 

donc après émettez un appel ajax à cette action, je vérifie la réponse pour vrai/faux et d'erreur d'affichage ou messages succès.

Problème:

Maintenant, ce qui est arrivé est que je commencé à me exceptions dans mon action, et l'action revenait toujours faux, et le message d'erreur a été affichée. Mais je n'ai pas pu trouver pourquoi?

Alors je me demandais s'il y a une structure de réponse api standard que tout le monde suit?

je devais d'abord venu avec cette idée d'avoir chaque action api web pour retourner cette classe

public class OperationStatus 
{ 
    public bool Result { get; set; } // true/false 
    public string Status { get; set; } // success/failure/warning 
    public List<string> WarningMessages { get; set; } 
    public List<string> ErrorMessages { get; set; } 
    public string OtherDetails { get; set; } 
} 

Ce changement serait un changement majeur et serait temps et de ressources, donc je pensais que son mieux avoir une deuxième/troisième/quatrième opinion à ce sujet.

S'il vous plaît mettez quelques réflexions à ce sujet.

Mise à jour:

Avec un peu little help de Mark Jones, je suis venu avec cette

[ActionName("UpdateAccountDetails")] 
public HttpResponseMessage PostAccountDetails(SomeModel model) 
{ 
    bool updateStatus; 
    string errorMessage; 
    try{ 
     updateStatus = _customService.UpdateAccountDetails(model); 
     if(updateStatus) 
     { 
      return Request.CreateResponse(HttpStatusCode.OK); 
     } 
     return Request.CreateResponse(HttpStatusCode.InternalServerError); 
    } 
    catch(Exception exception) 
    { 
     errorMessage = exception.Message; 
     return Request.CreateResponse(HttpStatusCode.InternalServerError, errorMessage); 
    } 

    return updateStatus; 
} 

Toute pensée à ce sujet?

+0

Ce post peut vous donner quelques idées sur la mise en œuvre de la gestion des erreurs avec WebAPI: http: //blogs.msdn.com/b/youssefm/archive/2012/06/28/error-handling-in-asp-net-webapi .aspx –

+0

Vous devriez également regarder les suggestions de Kevin et Filip ci-dessous. L'implémentation d'un filtre d'exception est une bonne idée et vous devriez envisager de lancer une exception HttpResponseException lorsqu'une erreur se produit afin de ne pas avoir à changer le type de retour sur votre signature d'action. –

Répondre

26

Vous devriez éviter d'utiliser try/catch dans l'action du contrôleur.

Il existe plusieurs façons de gérer votre problème. La solution serait sans doute plus simple et la plus propre à utiliser un ActionFilter pour gérer les exceptions, quelque chose le long des lignes de:

public class ExceptionAttribute : ExceptionFilterAttribute 
{ 
    public override void OnException(HttpActionExecutedContext context) 
    { 
     Debug.WriteLine(context.Exception); 

     throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError) 
     { 
      Content = new StringContent("An error occurred!"), 
      ReasonPhrase = "Deadly Exception" 
     }); 
    } 
} 

Ensuite, vous pouvez simplement décorer votre action avec [ExceptionAttribute]. Bien sûr, vous pouvez étendre ce comportement différemment pour différents types d'exceptions (exceptions métier, exceptions de données, exceptions E/S, etc.) et renvoyer des codes d'état et des commentaires différents en fonction de ces exceptions.

Je vous recommande de lire un excellent article par Fredrik Normen - "API Web ASP.NET Gestion des exceptions"http://weblogs.asp.net/fredriknormen/archive/2012/06/11/asp-net-web-api-exception-handling.aspx.

Il fournit un excellent aperçu des techniques de gestion des exceptions pour l'API Web.

+0

Excellente recommandation et merci de poster sur l'article de Fredrik Normen! – seebiscuit

4

au lieu de retourner un HttpResponseMessage je garderais l'API est le même et il suffit de jeter un HttpResponseException quand vous attrapez une exception. Quelque chose comme ceci:

throw new HttpResponseException(
    new HttpResponseMessage(HttpStatusCode.InternalServerError) 
     { ReasonPhrase = errorMessage }); 

De cette façon, vous ne changez pas la définition de votre API et travaillerez avec vos actions GET et où vous retournez un objet qui doit être publié en feuilleton. Si vous utilisez la méthode JQuery ajax pour envoyer la requête, votre gestionnaire error l'attrapera et vous pouvez récupérer le message texte dans le paramètre errorThrown et le gérer en conséquence.

Questions connexes