Last active
August 29, 2015 14:20
-
-
Save spaceCamel/9f66c60d15fdbfb2fe7f to your computer and use it in GitHub Desktop.
Jackson and floating-point numbers
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import com.fasterxml.jackson.core.JsonGenerator | |
import com.fasterxml.jackson.core.JsonProcessingException | |
import com.fasterxml.jackson.databind.JsonSerializer | |
import com.fasterxml.jackson.databind.ObjectMapper | |
import com.fasterxml.jackson.databind.SerializerProvider | |
import com.fasterxml.jackson.databind.module.SimpleModule | |
import spock.lang.Specification | |
import java.math.RoundingMode | |
class JacksonFloatingPointNumberTest extends Specification | |
{ | |
static floatingPointFix = new SimpleModule("floating-point-rounding-fix").with { module -> | |
module.addSerializer(Double.class, new JsonSerializer<Double>() { | |
@Override | |
void serialize(final Double value, final JsonGenerator jgen, final SerializerProvider provider) throws IOException, JsonProcessingException | |
{ | |
def asBD = value.toBigDecimal() | |
def truncated = asBD.scale() > 4 ? asBD.setScale(4, RoundingMode.HALF_EVEN) : asBD | |
def numericString = truncated.stripTrailingZeros().toPlainString() | |
jgen.writeNumber(numericString) | |
} | |
}) | |
module.addSerializer(Float.class, new JsonSerializer<Float>() { | |
@Override | |
void serialize(final Float value, final JsonGenerator jgen, final SerializerProvider provider) throws IOException, JsonProcessingException | |
{ | |
def asBD = value.toBigDecimal() | |
def truncated = asBD.scale() > 4 ? asBD.setScale(4, RoundingMode.HALF_EVEN) : asBD | |
def numericString = truncated.stripTrailingZeros().toPlainString() | |
jgen.writeNumber(numericString) | |
} | |
}) | |
return module | |
} | |
def mapper = new ObjectMapper() | |
def 'serialize float'() | |
{ | |
given: | |
float amount = 545.51f | |
def sourceMap = [amount: amount] | |
when: | |
def json = mapper.writeValueAsString(sourceMap) | |
then: | |
json == '{"amount":545.51}' | |
} | |
def 'serialize double'() | |
{ | |
given: | |
double amount = 545.51d | |
def sourceMap = [amount: amount] | |
when: | |
def json = mapper.writeValueAsString(sourceMap) | |
then: | |
json == '{"amount":545.51}' | |
} | |
def 'serialize float upcasted to double'() | |
{ | |
given: | |
double amount = 545.51f | |
def sourceMap = [amount: amount] | |
when: | |
def json = mapper.writeValueAsString(sourceMap) | |
then: | |
json == '{"amount":545.51}' | |
} | |
def 'serialize float upcasted to double with fix'() | |
{ | |
given: | |
double amount = 0.255f | |
def sourceMap = [amount: amount] | |
mapper.registerModule(floatingPointFix) | |
when: | |
def json = mapper.writeValueAsString(sourceMap) | |
then: | |
json == '{"amount":0.255}' | |
} | |
def 'serialize double downcated to float'() | |
{ | |
given: | |
float amount = 545.51d | |
def sourceMap = [amount: amount] | |
when: | |
def json = mapper.writeValueAsString(sourceMap) | |
then: | |
json == '{"amount":545.51}' | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment