0

I'm using Tomee 8 as an application server and I have this trouble when my rest service returns a BigDecimal.

This is my service:

import javax.ws.rs.Consumes;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;

@Path("/v0")
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public class RSDummyCheck {

    @Path("/dummyCheck")
    @POST
    public Response dummyCheck(Dummy input){
        Dummy resultado = input;
        return Response.ok(resultado, "application/json").build();
    }
 }

The input is

import java.math.BigDecimal;
import java.util.Date;

public class Dummy{
    BigDecimal numero;

    public BigDecimal getNumero() {
        return numero;
    }
    public void setNumero(BigDecimal numero) {
        this.numero = numero;
    }
    
    public String toString() {
        return "Dummy numero:"+this.numero

    }
}

So, when I try the service, sending this json message:

{
    
    "numero": 23.4
    
}

I got this response

{
    "numero": "23.4"
}

But I expect to receive the same without the quotes, not a String.

Tomee 8 by default uses Apache Johnzon as JSON provider. Is there the problem?

What is wrong here? Why does the return value appear as a string and not as a decimal?

rfrp
  • 167
  • 1
  • 9
  • 1
    Javascript numeric literals are generally treated as IEEE754 doubles. The whole point of BigDecimal is to have more precision than that. What you're asking for is akin to: "Can my JSON library by default just serialize a date into just the year, and toss away the rest?" - it's a weird question. You sure you want to toss away all that precision? Why not just stop using BigDecimal in java if that's what you desire to do? – rzwitserloot May 06 '22 at 15:12
  • The behavior can probably be configured. But we would need to know the JSON provider you are using. – Paul Samsotha May 06 '22 at 20:08
  • @PaulSamsotha the provider is Apache Johnson which is default in Tomee. – rfrp May 08 '22 at 01:46

1 Answers1

1

You need to use a MapperConverter object.

For example, you could implement the ObjectConverter.Codec interface.

This code can be useful for your requirement.

For example: You can include @JohnzonConverter(MyBigDecimalValueConverter.class) on the desired fields.

public class MyBigDecimalValueConverter implements ObjectConverter.Codec<BigDecimal> {

    @Override
    public void writeJson(BigDecimal value, MappingGenerator jsonbGenerator) {
        jsonbGenerator.getJsonGenerator().write(value);
    }

    @Override
    public BigDecimal fromJson(JsonValue jsonValue, Type targetType, MappingParser parser) {
        return parser.readObject(jsonValue, targetType);
    }
}
Laurel
  • 5,965
  • 14
  • 31
  • 57
Juan Pablo
  • 36
  • 3