Java 如何优化Tomcat的进给拉力

Java 如何优化Tomcat的进给拉力,java,tomcat,akka,Java,Tomcat,Akka,我们有一个向用户提供提要的移动应用程序。feedrestapi是在tomcat上实现的,它并行地调用不同的数据源,如Couchbase、MYSQL来呈现内容。下面给出了简单的代码: Future<List<CardDTO>> pnrFuture = null; Future<List<CardDTO>> newsFuture = null; ExecutionContext ec = ExecutionContexts.fromExecutorS

我们有一个向用户提供提要的移动应用程序。feedrestapi是在tomcat上实现的,它并行地调用不同的数据源,如Couchbase、MYSQL来呈现内容。下面给出了简单的代码:

Future<List<CardDTO>> pnrFuture = null;
Future<List<CardDTO>> newsFuture = null;

ExecutionContext ec = ExecutionContexts.fromExecutorService(executor);

final List<CardDTO> combinedDTOs = new ArrayList<CardDTO>();

// Array list of futures 
List<Future<List<CardDTO>>> futures = new ArrayList<Future<List<CardDTO>>>();

futures.add(future(new PNRFuture(pnrService, userId), ec)); 
futures.add(future(new NewsFuture(newsService, userId), ec)); 
futures.add(future(new SettingsFuture(userPreferenceManager, userId), ec)); 

Future<Iterable<List<CardDTO>>> futuresSequence = sequence(futures, ec); 

// combine the cards 
Future<List<CardDTO>> futureSum =  futuresSequence.map( 
        new Mapper<Iterable<List<CardDTO>>, List<CardDTO>>() {
            @Override 
            public List<CardDTO> apply(Iterable<List<CardDTO>> allDTOs) { 
                for (List<CardDTO> cardDTOs : allDTOs) {
                    if (cardDTOs != null) {
                        combinedDTOs.addAll(cardDTOs);
                    } 
                } 

                Collections.sort(combinedDTOs);
                return combinedDTOs;
            } 
        } 
); 

Await.result(futureSum, Duration.Inf());  
return combinedDTOs; 
Future pnrFuture=null;
Future newsfourture=null;
ExecutionContext ec=ExecutionContext.fromExecutorService(executor);
最终列表CombinedTos=新的ArrayList();
//期货数组列表
列表期货=新的ArrayList();
future.add(future(新的PNRFuture(pnrService,userId),ec));
future.add(future(newnewsfourture(newservice,userId),ec));
添加(future(新设置future(userPreferenceManager,userId),ec));
未来未来序列=序列(未来,ec);
//组合卡片
Future futureSum=futuresquence.map(
新映射器(){
@凌驾
公共列表应用(Iterable allDTOs){
对于(列表cardDTOs:allDTOs){
if(cardDTOs!=null){
合并的ToS.addAll(cardDTOs);
} 
} 
Collections.sort(combinedtos);
返回组合的TOS;
} 
} 
); 
wait.result(futureSum,Duration.Inf());
返回组合的TOS;
现在,每个请求大约有4-5个并行任务。但随着我们在feed中引入新种类的项目,预计它将增长到几乎20-25个并行任务

我的问题是,我如何改进这个设计?在Tomcat中需要什么样的调优来确保这样的20-25个并行调用能够在重负载下得到最佳服务


我知道这是一个广泛的话题,但任何建议都会非常有用。

Tomcat只管理传入的HTTP连接并来回推送字节。没有任何Tomcat优化可以使您的应用程序运行得更好

如果您需要为每个传入的HTTP请求运行25个并行进程,并且您认为这太疯狂了,那么您需要重新考虑应用程序的工作方式


没有任何tomcat配置可以帮助您解决问题。

看起来您使用的是Akka,但实际上并不支持Actor模型,这样做可能会增加并行性,从而提高应用程序的可扩展性

如果是我,我会将RESTAPI中的请求转交给一个或多个协调参与者池,这些参与者将异步处理请求。使用Spring的RestController,这可以通过
可调用的
延迟结果
来实现,但在您使用的任何框架中,显然都会有一个等价物

然后,这个协调参与者将把处理交给负责i/O绑定任务的其他参与者(即工人)(最好使用他们自己的调度程序来确保其他CPU绑定线程不会被阻塞),并用他们的结果响应协调器


一旦所有工作人员都获取了数据并向协调员回复了结果,那么原始请求就可以使用完整的结果集完成。

我知道您是通过移动应用程序调用此消息的,并且提要的数量可能会增加

根据返回的数据量,是否可以在同一调用中返回某些提要的结果? 这样服务器就完成了工作。 您可以控制服务器-您无法控制用户设备及其连接速度

正如nickebbit所建议的,像DefferedResult这样的东西很容易实现。 这些提要中的数据是否可能不会快速更新?如果是这样-您应该调查EHCache和@Cacheable注释的使用情况

您可以想出一个解决方案,用户总是从tomcat服务器中提取内容的缓存版本。但是您的tomcat服务器在后台不断更新缓存


这是一项额外的工作-但在一天结束时,如果用户体验不快-用户将不想使用此应用程序

是否要求在一个请求中返回所有数据?是的,返回完整的提要。在未来,它可能会被分页…@madhur ahuja:有很多东西可以改进,以使这样的设计更好-在我看来,你似乎正在尝试实现类似[(微服务)的东西将不同的数据源聚合到一个提要中。问题是…tomcat是您最小的问题。因为每个远程服务都可能失败,所以您需要关注系统的弹性,才能真正实现这样的设计。我首先想到的是断路器和平衡器,但它们超出了问题的范围:)