java - Spring boot 限制控制器中特定 API 的并发调用次数
问题描述
我有一个基于 sprint boot (v1.5.15) 的 Restful 应用程序,它提供基于用户的服务,特别是登录和获取用户详细信息。
登录活动稍微繁重,因为获取用户详细信息 api 的重量很轻。
我有一个类似于这个的控制器
@RestController
public class UserController{
@PostMapping("/login")
public LoginResponse userLogin(@RequestBody LoginRequest loginRequest){
...
}
@GetMapping("/users/{id}")
public LoginResponse userIdGet(@PathVariable("id") String id){
...
}
}
有什么办法可以限制对/login
api 的并发调用数。基本上我想限制这个说 x 因为/users/{id}
可以处理大约 10 倍的调用的相同资源。
该应用程序使用嵌入式 tomcat 服务器,我知道server.tomcat.max-connections
,但是这些限制在应用程序级别而不是 API 上的调用。server.tomcat.max-threads
server.tomcat.min-spare-threads
解决方案
有一些解决方案可以限制活动连接的数量,请参见https://dzone.com/articles/how-to-limit-number-of-concurrent-user-session-in。
但是,afaik,这样的解决方案只是拒绝进一步的请求。
如果您不喜欢拒绝请求,您可能会通过使用应用程序范围的固定线程池 ExecutorService ( https://docs.oracle.com/javase/7/docs/api/java/util/concurrent /Executors.html#newFixedThreadPool(int))并将您的请求正文提交到该线程池并立即在返回的 Future 上调用 get 。
所以你可以更换
@PostMapping("/api/xyzMethod")
public Response xyzMethod(@RequestBody Request request) {
return handleXyzMethod(request); });
}
经过
@PostMapping("/api/xyzMethod")
public Response xyzMethod(@RequestBody Request request) throws InterruptedException, ExecutionException {
return xyzMethodExecutor.submit(() -> { return handleXyzMethod(request); }).get();
}
和一些
private static ExecutorService xyzMethodExecutor = Executors.newFixedThreadPool(10);
一个缺点是用户可能必须等待回复和/或多个请求将填充线程池队列,直到服务变得(太)无响应。因此,也许您必须在 FutureTasks 上为该解决方案赋予某种超时,或者将这两种解决方案结合起来(即对并发会话的数量也有更大的限制)。
推荐阅读
- c++ - 为什么不能正确地将圆括号视为构造函数调用?
- react-navigation - 确保在 initialRouteName 中指定的路由始终添加为堆栈中的第一个屏幕
- python - 熊猫。根据行数据选择列名
- python - 关闭正在运行的python线程的问题
- java - NumberFormate 异常
- javascript - 将参数从 URL 添加到元素并滚动到元素
- python - 对 post 请求使用异步、多处理或多线程是否好?
- pointers - 给定两个变量,在计算机的大脑(内存)中找到它们的距离(以字节为单位)
- wpf - 将变量绑定到 Powershell 中的组合框和文本框
- reactjs - 如何优化大型 lang.json 文件以减小包大小