【问题标题】:Async API giving worse performance异步 API 性能更差
【发布时间】:2017-08-18 01:45:21
【问题描述】:

有趣的是,我认为有 255 个并发用户,异步 API 会有更好的性能。这是我的 Spring 服务器中的 2 个端点:

@RequestMapping("/async")
public CompletableFuture<String> g(){
    CompletableFuture<String> f = new CompletableFuture<>();
    f.runAsync(() -> {
        try {
            Thread.sleep(500);
            f.complete("Finished");
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    });

    return f;
}

@RequestMapping("/sync")
public String h() throws InterruptedException {
    Thread.sleep(500);
    return "Finished";
}

在/async 中,它在不同的线程上运行它。我正在使用Siege 进行负载测试,如下所示:

siege http://localhost:8080/sync --concurrent=255 --time=10S &gt; /dev/null

对于async 端点,我得到了27 hits 的事务号

对于sync 端点,我得到了1531 hits 的事务号

那为什么会这样呢?为什么异步端点不能处理更多事务?

【问题讨论】:

    标签: java spring api testing asynchronous


    【解决方案1】:

    因为异步端点使用共享(小ForkJoinPool.commonPool())线程池来执行休眠,而同步端点使用应用程序服务器的较大线程池。由于公共池非常小,您一次可能运行 4-8 个操作(好吧,如果您将睡眠称为操作),而其他人则在等待轮到他们进入池中。您可以将更大的池与CompletableFuture.runAsync(Runnable, Executor) 一起使用(您也调用了错误的方法,它是一个返回CompletableFuture 的静态方法)。

    异步并不是一种神奇的“让事情变得更快”的技术。您的示例存在缺陷,因为所有请求都需要 500 毫秒,而您只是在异步请求中增加了开销。

    【讨论】:

    • “您的示例存在缺陷,因为所有请求都需要 500 毫秒,而您只是在异步请求中增加了开销。”是的,都需要 500 毫秒,但在某些时候,我希望异步会更快。如何进行公平的一般测试?除了使用 Thread.sleep,我还能用什么来准确测试?
    • 有长期运行和短期运行的操作。异步并不是我已经说过的“让所有事情变得更快”的魔法。
    • 是的,我只是出于好奇才这样做。当您说“多头和空头”时,您的确切意思是什么?测试中应该有多少并发用户?
    • 我的意思是长跑和短跑。而不是单个操作需要 500 毫秒。
    • 对不起,我好像没听懂。介意举个例子吗?我很感激
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-10-01
    • 2013-07-08
    • 2015-10-28
    • 2013-07-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多