返回

优化接口性能只改了5行代码,吞吐量提升10多倍,背后思路太绝了!

后端

只改了五行代码接口吞吐量提升了10多倍

我们都知道对一个接口进行压测,其调优的方向无非是:

  1. 数据库优化
  2. 代码优化
  3. 缓存优化
  4. 服务优化(服务配置、架构设计、负载均衡等)

根据我们的场景,服务架构、负载均衡、缓存我们都不需要去关注,所以我们把目标瞄准了数据库、代码、服务配置这三个方面。

数据库

我们首先对接口做了SQL抓包,发现接口一次请求会产生四次数据库操作,而且每次操作都是全表扫描。

优化思路非常明显,加索引!针对全表扫描,我们只需要根据WHERE条件的字段加上索引即可。

优化后,接口的响应时间从500ms降到了100ms。

但是问题并没有结束,随着压测的进行,数据库的并发数上升,响应时间又升到了200ms。

原因很简单,索引优化只能解决查询效率的问题,而随着并发数的上升,数据库的锁机制会成为新的瓶颈。

解决方案,分库分表

分库分表虽然是一个治标不治本的方法,但短期内确实可以解决并发问题。

分库分表后,接口的响应时间稳定在了100ms以内。

代码

接口的代码我们也做了进一步的优化。

原先的代码是这样的:

public String getXXX() {
    String xxx = db.queryXXX();
    return xxx;
}

优化后的代码是这样的:

public String getXXX() {
    String xxx = db.queryXXX();
    if (xxx == null) {
        return "";
    }
    return xxx;
}

我们发现,接口返回的数据可能是空,但原本的代码并没有对返回数据做非空判断,这样就会导致接口返回null,对于调用方来说,接口的异常处理会非常麻烦。

优化后的代码对返回数据做了非空判断,接口返回的数据始终是一个合法的字符串,调用方的异常处理就简单了很多。

服务配置

在对数据库和代码进行了优化之后,接口的响应时间已经稳定在了100ms以内,但是随着压测线程数的不断增加,接口的响应时间又开始上升。

这个时候,我们就需要对服务配置进行优化了。

我们把服务的线程池调大,把服务的最大连接数调大,把服务的队列长度调大。

优化后,接口的响应时间稳定在了50ms以内。

总结

通过对数据库、代码、服务配置这三个方面的优化,我们把接口的吞吐量提升了10多倍。

本次优化过程也给我们带来了一些启示:

  1. 接口调优是一个系统性的工程,需要从数据库、代码、服务配置等多个方面入手。
  2. 接口调优是一个渐进的过程,需要不断地进行压测和优化,才能达到最终的目标。
  3. 接口调优需要结合业务场景,不能盲目地照搬别人的经验。