目录
现象
理论分析
代码分析
解决方案
方案一:直接修改pollingConnectionManager
方案二:修改HttpClient
参考
现象
线上共有5个类似服务,但是只有流量较大的服务会出现成功率的问题。
问题的表现主要是在GetFile(fileId=AgACAgUAAxkDAAEbP1JlJPxyJM82phEKhYYZYfY9ozwkOgACV7YxGyAgKVWHvIUKD2IoYQEAAwIAA3kAAzAE)时会失败。具体如下:
[2023-10-10 07:26:16.985][ERROR][pool-9-thread-14][pool-9-thread-14][][c.t.c.t.SpringTelegramWebhook:122][SpringTelegramWebhook.getFile TelegramApiException][GetFile(fileId=AgACAgUAAxkDAAEbP1JlJPxyJM82phEKhYYZYfY9ozwkOgACV7YxGyAgKVWHvIUKD2IoYQEAAwIAA3kAAzAE)][500][org.telegram.telegrambots.meta.exceptions.TelegramApiException: Unable to execute getFile method
at org.telegram.telegrambots.bots.DefaultAbsSender.sendApiMethod(DefaultAbsSender.java:1117)
at org.telegram.telegrambots.meta.bots.AbsSender.execute(AbsSender.java:64)
at com.turbo.commons.telegram.SpringTelegramWebhook.lambda$getFile$4(SpringTelegramWebhook.java:119)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at java.lang.Thread.run(Thread.java:748)
Caused by: org.apache.http.conn.ConnectionPoolTimeoutException: Timeout waiting for connection from pool
at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.leaseConnection(PoolingHttpClientConnectionManager.java:316)
at org.apache.http.impl.conn.PoolingHttpClientConnectionManager$1.get(PoolingHttpClientConnectionManager.java:282)
at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:190)
at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:186)
at org.apache.http.impl.execchain.RetryExec.execute(RetryExec.java:89)
at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110)
at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:185)
at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:83)
at org.telegram.telegrambots.bots.DefaultAbsSender.sendHttpPostRequest(DefaultAbsSender.java:1149)
at org.telegram.telegrambots.bots.DefaultAbsSender.sendMethodRequest(DefaultAbsSender.java:1145)
at org.telegram.telegrambots.bots.DefaultAbsSender.sendApiMethod(DefaultAbsSender.java:1114)
... 6 more
其中,关键错误信息:
Caused by: org.apache.http.conn.ConnectionPoolTimeoutException: Timeout waiting for connection from pool。
业务代码如下:
private BufferedImage getImageByFileId(String fileId, DefaultTelegramBot bot) throws Exception {
GetFile getFile = new GetFile();
getFile.setFileId(fileId);
InputStream inputStream = bot.getFile(getFile);
return ImageIO.read(inputStream);
}
理论分析
出现Timeout waiting for connection from pool异常的原因主要有二:
-
连接没关闭,资源没释放。
-
pool的连接数设置太小
可以看到第1条,是老生常谈的资源关闭问题。博主在开发的时候,正是因为不需要知道调用的返回结果,所以没有对Response进行处理,所以资源并没有释放,导致后面再使用HttpClient,就拿不到连接了
第2条&