Springboot全局配置實現BigDecimal返回前端去除小數點后多余的零
一、前言
我們在使用BigDecimal來記錄數值時,經常會有一個問題,就是小數點后多余的0!
當前如果你們是金額,保留兩位小數,展示多余的0是沒有問題的!可以看一下銀行卡是會顯示到分的!
小編的這里不是這種的,是要求保留八位小數,即使前端輸入100.1。保存到數據庫時就會變為:100.10000000,前端查詢出來肯定就是100.10000000。非常的臃腫,我們就需要去掉一下!
二、解決方案
分為兩種方案:
- 按需進行去除0。
- 全局BigDecimal全部去除0。
各有各的優缺點,就是看你們系統的要求了!
小編這里是有的允許保留0的,不需要的咱們單獨處理。所以咱們先演示第一種!
1、第一種方案
「編寫自定義序列化器:BigDecimalSerializer」
/**
* BigDecimal序列化器
* @author wangzhenjun
* @date 2023/5/17 16:29
*/
public class BigDecimalSerializer extends JsonSerializer<BigDecimal> {
@SneakyThrows
@Override
public void serialize(BigDecimal bigDecimal, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) {
if (null != bigDecimal ) {
String plainString = bigDecimal.stripTrailingZeros().toPlainString();
jsonGenerator.writeString(plainString);
} else {
jsonGenerator.writeString(BigDecimal.ZERO.toPlainString());
}
}
}
在需要的對象上添加注解@JsonSerialize即可:
/**
* @author wangzhenjun
* @date 2023/5/17 16:51
*/
@Data
public class Big {
@JsonSerialize(using = BigDecimalSerializer.class)
private BigDecimal price;
}
測試一下:
@GetMapping("/big")
public Result big(){
Big big = new Big();
big.setPrice(new BigDecimal("1.20"));
return Result.success(big);
}
我們可以看到正常的去除多余的0,我們會發現原來的BigDecimal變為了字符串,其實這個也是正常的,在我們系統里會配置上,把Long和BigDecimal返回前端的時候都會變為字符串,防止精度丟失。
想詳細了解的可以看看文章,趕時間的,小編在下面給出來了,添加一個配置類即可!
@Configuration(proxyBeanMethods = false)
@ConditionalOnClass(ObjectMapper.class)
@AutoConfigureBefore(JacksonAutoConfiguration.class)
public class JacksonConfiguration {
@Bean
@ConditionalOnMissingBean
public Jackson2ObjectMapperBuilderCustomizer customizer() {
return builder -> {
builder.locale(Locale.CHINA);
builder.timeZone(TimeZone.getTimeZone(ZoneId.systemDefault()));
// 設置日期格式
builder.simpleDateFormat(DatePattern.NORM_DATETIME_PATTERN);
// 解決long類型損失精度
builder.serializerByType(Long.class, ToStringSerializer.instance);
// 解決BigDecimal類型損失精度
builder.serializerByType(BigDecimal.class, ToStringSerializer.instance);
// 日期格式自定義類
builder.modules(new PigJavaTimeModule());
};
}
}
2、第二種方式
我們只需要進行序列化的時候去除一下即可,這是全局的BigDecimal都會去除多余0,大家按需使用,以免造成不必要的事故!
/**
* 全局序列化配置
* @author wangzhenjun
* @date 2023/5/19 17:11
*/
@Configuration
public class JacksonConfig {
@Bean
public ObjectMapper objectMapper() {
ObjectMapper objectMapper = new ObjectMapper();
SimpleModule module = new SimpleModule();
module.addSerializer(BigDecimal.class, new JsonSerializer<BigDecimal>() {
@Override
public void serialize(BigDecimal value, JsonGenerator gen, SerializerProvider serializers) throws IOException {
if (value != null) {
gen.writeString(value.stripTrailingZeros().toPlainString());
}
}
});
objectMapper.registerModule(module);
return objectMapper;
}
}
我們再次測試,我把上一種方式的寫法去掉了哈!
我們可以看到也是沒有問題的哈!
三、總結
通過本篇博客的介紹,我們知道了兩種解決方式!可以對BigDecimal類型進行格式化,去除前端展示中多余的0。這樣能夠優化前端展示效果,提高用戶體驗。這個兩個方法都簡單易用,而且具有通用性,適合大部分項目使用。
當然,在實際開發中,還有很多其他的格式化方式和技巧可以使用,比如使用前端框架的過濾器、使用JavaScript的toFixed()函數等等。不過,無論使用哪種方式,我們要做到的是盡可能地避免前端展示中出現多余的0,保證用戶體驗。
最最重要的是符合業務要求!
希望本篇博客的介紹能夠對大家有所幫助。