centos7 tomcat_CentOS7下Tomcat应用容器抛出Too many open files问题
背景
在實際開發中有一款設備管理軟件,一般情況下接入的設備并不多,最多幾十臺;最近有一個項目中,需要接入2000臺這樣的設備,運行一段時間后,會大量拋出Too many open files;導致設備無法正常使用,重啟服務器后才恢復。
Tomcat下拋出Too many open files問題解析
分析
查看 ulimit -n 指令,發現文件句柄默認是1024,查看對應Tomcat進程(如下)
cat /proc/1787/limits #查看當前應用進程的句柄是4096lsof -p 1787 | wc -l #其中1787是對應的進程發現已經超出4096了,導致后續已經無法操作文件句柄了,所以系統拋出異常,設備故障發生。
什么時候發生的
經過排查,發現是由一個操作引發的“時間同步”操作---因為系統是局域網內,設備終端的時間需要和系統保持一致,所以有時間同步操作這一功能,由于沒有壓測大量設備的情況,所以代碼中也存在一定的隱患
private static final ThreadPoolExecutor deviceOpeartor=(ThreadPoolExecutor)Executors.new CachedThreadPool(); publicstaticFutureaddTask(PoolTypetype,Callabletask){ ThreadPoolExecutorpool=getPool(type); returnpool.submit(task); }采用了默認的線程池newCachedThreadPool,池的大小是INT.MAX最大值(就是沒限制了), 導致時間同步的任務加進去后,一下子全部執行了。
同時,Tomcat對webapp有一套自己的WebappClassLoader,它在啟動的過程中會打開應用依賴的jar包來加載class信息, 但是過一段時間就會把打開的jar包全部關閉從而釋放資源。然而如果后面需要加載某個新的class的時候,會把之前所有的jar包全部重新打開一遍, 然后再從中找到對應的jar來加載。加載完后過一段時間會再一次全部釋放掉。
所以應用依賴的jar包越多,同時打開的文件句柄數也會越多。 2000臺設備時間同步,一下子打開了過多的文件,導致文件句柄一下子超出了。故障就發生了
如何解決
1、代碼優化
首先是代碼層面的優化,采用阻塞隊列
private static final ThreadFactory namedThreadFactory = new ThreadFactoryBuilder().setNameFormat("device-pool-%d").build();private static final ThreadPoolExecutor deviceThreadPool = new ThreadPoolExecutor(5, 100, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingDeque(2048), namedThreadFactory, new ThreadPoolExecutor.AbortPolicy());同時對于頻繁的點擊時間同步按鈕,需要有機制通知之前隊列中的任務還在執行,等待任務全部執行完畢后,再下一次操作
2、系統層面的調優
在不同批次的服務器上,有的服務器Max Open Files設置是65536;
但是一批新機器上的Max OpenFiles都被誤設置為4096了。
這個需要運維幫忙重新修復一下,需要重啟才會生效;具體的操作可以如下參考:
追加linux系統操作的句柄數 vim /etc/security/limits.conf追加* soft nofile 65536* hard nofile 65536星號代表全局,soft為軟件,hard為硬件,nofile為這里指可打開文件數。
配置修改完之后,需要重啟后生效 以上操作是開發人員在排查的過程中可以自己來設置,具體系統層面的最好運維出面
#############################################################
要使limits.conf文件配置生效,必須要確保pam_limits.so文件被加入到啟動文件中。 vim /etc/pam.d/login session required /lib/security/pam_limits.so注意:這個一般最好不要編輯,會導致系統問題(可能無法啟動,這個最好由運維來操作)
有時,發現上面設置了還是無效,還有一個辦法,在Tomcat下bin中的startup.sh中來追加一行配置
ulimit -n 40960 #在os400=false這一行之前,加上文件句柄數,這個是針對當前Tomcat這個進程下的 os400=false在實際使用過程中,會遇到各式各樣的問題,嘗試不同的方法去分析解決它
總結
以上是生活随笔為你收集整理的centos7 tomcat_CentOS7下Tomcat应用容器抛出Too many open files问题的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 为什么疫情会导致房价下跌呢?
- 下一篇: 简单阻容降压电路图_X2安规电容用于阻容