Mohamed Salah Mohamed Salah - 4 months ago 23
JSON Question

Serialize custom exception to JSON with web api

I need to show custom property added to custom exception

ModelException
at the output json of my
WebApi
. So I created custom exception class as follows

[Serializable]
public class ModelException : System.Exception
{
private int exceptionCode;
public int ExceptionCode
{
get
{
return exceptionCode;
}
set
{
exceptionCode = value;
}
}

public ModelException() : base() { }

public ModelException(string message) : base(message) { }

public ModelException(string format, params object[] args) : base(string.Format(format, args)) { }

public ModelException(string message, System.Exception innerException) : base(message, innerException) { }

public ModelException(string format, System.Exception innerException, params object[] args) : base(string.Format(format, args), innerException) { }


protected ModelException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
if (info != null)
{
int result = 0;
int.TryParse(info.GetString("ExceptionCode"), out result);
this.exceptionCode = result;
}
}

[SecurityPermissionAttribute(SecurityAction.Demand, SerializationFormatter = true)]
public override void GetObjectData(SerializationInfo info, StreamingContext context)
{
if (info != null)
{
info.AddValue("ExceptionCode", this.exceptionCode);
}

base.GetObjectData(info, context);
}

public ModelException(string message, int exceptionCode)
: base(message)
{
this.exceptionCode = exceptionCode;
}
}


then add the following configration to my
WebApiConfig


config.Formatters.JsonFormatter.SerializerSettings.Formatting = Formatting.Indented;
config.Formatters.JsonFormatter.SerializerSettings.ContractResolver = new DefaultContractResolver()
{
IgnoreSerializableInterface = true
};


the issue here is the new overidden constructor with
SerializationInfo
parameter is not fired and the newly custom property is not appear in the returned
Json
from
WebApi

Answer

Thanks to @MrinalKamboj

In order to change the output Json of Web API in the case of Exception. I did the following changes to solve this

  1. Implement my Custom Exception (ModelException) as in my Question
  2. as per @MrinalKamboj comment i created the following

    public class NotImplExceptionFilterAttribute : ExceptionFilterAttribute 
    {
        public override void OnException(HttpActionExecutedContext context)
        {
             if (context.Exception is ModelException)
             {
                ModelException exception = (ModelException)context.Exception;
                HttpError error = new HttpError();
                error.Add("Message", "An error has occurred.");
                error.Add("ExceptionMessage", exception.Message);
                error.Add("ExceptionCode", exception.ExceptionCode);
                error.Add("ExceptionType", exception.Source);
                error.Add("StackTrace", exception.StackTrace);
    
                context.Response = context.Request.CreateErrorResponse(HttpStatusCode.InternalServerError, error);
             }
        }
    }
    
  3. register the attribute to Web API as follows

    config.Filters.Add(new NotImplExceptionFilterAttribute());
    

The explanation of the issue

I want to change the output json resulted from Web API this will not be applicable by just implementing ISerializable we need to intercept the exception and change the output response of the json using HTTPErorr

Comments