使用 apachebench 和“ab -k -c 50 -n 1000000”选项(50 个并发线程)显示以下 2 种方法(手动和 spring 管理的序列化)之间的性能差异为 10 倍。通过配置Spring序列化是否可以达到相同的性能?
我正在 Windows 7、JDK8、i7-6700 上运行测试。嵌入式 Tomcat,与 Undertow 或 Jetty 的结果也类似。类似的 WildFly 10 JAX-RS 示例应用程序性能产生与手动 Spring 应用程序类似的结果,因此我认为 Spring 自动模式没有理由如此缓慢。
完整源代码:
@SpringBootApplication
@Controller
public class DemoApplication {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
ObjectMapper mapper = new ObjectMapper(new JsonFactory());
@RequestMapping(value = "/auto", produces = "application/json; charset=utf-8")
@ResponseBody
public Lol automaticSerialization() {
Lol lol = new Lol();
lol.a = UUID.randomUUID().toString();
lol.b = System.currentTimeMillis();
return lol;
}
@RequestMapping(value = "/manual", produces = "application/json; charset=utf-8")
@ResponseBody
public String manualSerialization() throws JsonProcessingException {
Lol lol = new Lol();
lol.a = UUID.randomUUID().toString();
lol.b = System.currentTimeMillis();
return mapper.writeValueAsString(lol);
}
public static class Lol {
String a;
long b;
public void setA(String a) {
this.a = a;
}
public void setB(long b) {
this.b = b;
}
public String getA() {
return a;
}
public long getB() {
return b;
}
}
}
最佳答案
我唯一的想法是 Spring 的默认 ObjectMapper
的配置与您在基准测试中使用的配置略有不同。就像评论中提到的那样,如果让 Spring 自动处理映射,您可能会看到一些开销,但它的影响不应超过百分之几。
为了确保比较公平,请将此 bean 定义添加到您的配置中:
@Bean
@Primary
ObjectMapper objectMapper() {
return new ObjectMapper(new JsonFactory());
}
并将 ObjectMapper mapper = new ObjectMapper(new JsonFactory());
替换为 Autowiring 字段:
@Autowired
ObjectMapper mapper;
并查看基准测试是否返回相同的值。
编辑
我想亲自验证这一点,所以我编写了一个 JMeter 计划,并执行每个端点 5kk 次,并有 1 分钟的预热时间。结果符合预期,方法之间没有重大差异:
Label,# Samples,Average,Min,Max,Std. Dev.,Error %,Throughput,KB/sec,Avg. Bytes
Auto Request,5000000,2,0,108,5.88,0.00%,15577.3,3088.08,203.0
Manual Request,5000000,2,0,149,5.99,0.00%,15660.2,2813.94,184.0
需要注意的重要一点是吞吐量差异 - 自动的 15577.3 与手动的 15660.2。
Here's my JMeter test plan ,如果你想自己测试一下,我是在端口 8081 上运行的。如果有时间,我会尝试另一个基准测试框架,也许是 Gadling。
关于spring - 为什么Spring MVC json序列化比手动调用jackson慢10倍?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38422716/