An extra .0 when returning JSON response that contains decimal type

Sometimes when we are designing API responses, we might want to return a JSON string which contains decimal-type field. We could easily represent the decimal-type field with string, so the response is in the following format:

{
    "amount": "3.00"
}

However, for whatever reason, if you want to return the amount field in decimal, and let's say it is very important the number of decimal place is shown correctly, there is some configuration required to get that right, as without any intervention, the client will end up seeing something as follow. *I am writing this based on the API designed using .NET's tech. stack.

{
    "amount": 3.0
}

Assuming we want the amount to be returned in 2 decimal places, 3.00, we could achieve that with the use of attribute. Let's start by creating a class with a property called amount.

public class Receipt
{
    public decimal amount { get; set; }
}

At some point, we want to serialize the above class into a JSON string which is to be returned as a response to an API request. The problem we want to solve is to prevent the default serializer from changing the number of decimal place, and the solution is to create a custom JsonConverter, which we place on the field that we want this custom converter to work on.

The following will represent the custom converter class.

/// <summary>
/// Prevent the existence of trailing .0 when serializing an object.
/// </summary>
public class DecimalOnlyJsonConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        return objectType == typeof(decimal);
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        writer.WriteRawValue(((decimal)value).ToString());
    }
}

We are writing the value of the decimal as a string, so that there will be no additional processing of the decimal value during serialization. We can place the above converter as an attribute.

public class Receipt
{
    [JsonConverter(typeof(DecimalOnlyJsonConverter))]
    public decimal amount { get; set; }
}

So there it is, you shall not see your decimal point being trimmed anymore.

Comments

Popular posts from this blog

ASP.NET Core service locator pattern

Ways to perform eager loading via NHibernate

Caching and generic query using NHibernate [.NET Core]