(一)容量規劃 6 條
軍規 1:線程池公式
maxThreads = ((并發峰值 × 平均 RT) / 1000) + 冗余 20 %;
踩坑:壓測 2000 QPS、RT 200 ms,理論 maxThreads=500,線上卻設 150 導致排隊。
軍規 2:Connector 選擇
? CPU < 4 核且短連接 → BIO(已廢棄)。
? 長連接、靜態文件多 → NIO。
? TLS 高并發 → NIO + JSSE 或 APR + OpenSSL。
軍規 3:內存預算
Heap = (并發請求數 × 平均對象大小 × 平均存活時間) / 2 + 峰值 Session 內存 + 50 % 安全墊。
軍規 4:Session 總數上限
maxActiveSessions=10000,超出后觸發 LRU 驅逐,防止 Map 膨脹。
軍規 5:靜態資源分離
Tomcat 只跑動態,靜態用 Nginx + CDN,CPU 下降 40 %。
軍規 6:容器啟動時間
SpringBoot FatJar 內嵌 Tomcat 12 s;外置 Tomcat + war 25 s;通過 jlink 裁剪模塊可降到 8 s。
(二)JVM 調優 7 條
軍規 7:G1 優于 Parallel
-XX:+UseG1GC -XX:MaxGCPauseMillis=200,Full GC 次數從 5 次/天降到 0。
軍規 8:Metaspace 初始值
-XX:MetaspaceSize=256m,防止啟動期頻繁 Full GC。
軍規 9:關閉顯式 GC
-XX:+DisableExplicitGC,防止 RMI 定時觸發 System.gc()。
軍規 10:JMX 安全
-Dcom.sun.management.jmxremote.authenticate=true -Dcom.sun.management.jmxremote.ssl=true。
軍規 11:GC Log 輪轉
-Xlog:gc*:file=/opt/logs/gc-%t.log:time,uptime:filecount=10,filesize=100M
軍規 12:OOM 自動 dump
-XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/opt/dump
軍規 13:容器感知
-XX:+UseContainerSupport -XX:MaxRAMPercentage=75.0
(三)線程與連接池 7 條
軍規 14:acceptorThreadCount=2 只在多核且 TLS 握手重 CPU 場景生效。
軍規 15:maxConnections 與 maxThreads 解耦
NIO 模式下 maxConnections=10000,maxThreads=200,防止 C10K 問題。
軍規 16:禁用 BIO
protocol="org.apache.coyote.http11.Http11NioProtocol" 顯式聲明,避免老版本默認 BIO。
軍規 17:Executor 共享
<Service name="Catalina">
軍規 18:StuckThreadDetectionValve
threshold=600,報警線程棧。
軍規 19:AsyncTimeout
NIO 模式下,異步 Servlet 默認 30 s 超時,可在 web.xml 覆蓋。
軍規 20:禁用 AJP
protocol="AJP/1.3" 如無反向代理,關閉端口 8009,防止 Ghostcat。
(四)日志與監控 6 條
軍規 21:AccessLogValve 格式
%{X-Forwarded-For}i %l %u %t "%r" %s %b %D,%D 記錄微秒級耗時。
軍規 22:RollingFileAppender
maxDays=7,防止磁盤爆。
軍規 23:Prometheus JMX Exporter
/opt/jmx_exporter/config.yml 暴露 tomcat_threadpool_currentThreadsBusy 等指標。
軍規 24:Grafana Dashboard
線程、Session、GC、響應碼 4 個維度,P95 響應時間告警閾值 1 s。
軍規 25:慢查詢定位
jstack 采樣 + Arthas trace javax.servlet.http.HttpServlet service 定位 SQL。
軍規 26:錯誤頁面自定義
web.xml 配置 <error-page>
(五)安全加固 7 條
軍規 27:刪除默認應用
webapps/docs、examples、ROOT、manager 全干掉。
軍規 28:關閉自動部署
<Host autoDeploy="false" deployOnStartup="false">
軍規 29:隱藏版本號
Server=" " 或自定義字符串,防止掃描。
軍規 30:啟用 HTTPS
<Connector SSLEnabled="true" sslProtocol="TLS" ciphers="TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256...">
軍規 31:SameSite Cookie
<Context useHttpOnly="true" sameSiteCookies="strict">
軍規 32:SecurityListener
<Listener className="org.apache.catalina.security.SecurityListener" checkedOsUsers="tomcat" />
軍規 33:文件上傳大小
<maxSwallowSize> 改為 10 MB,防止大文件占滿磁盤。
(六)故障演練 7 條
軍規 34:kill -3 模擬 Full GC 卡頓,驗證 HPA 是否及時擴容。
軍規 35:iptables -A INPUT -p tcp --dport 8080 -j DROP 模擬網絡分區,哨兵探測到后是否切流。
軍規 36:echo 3 > /proc/sys/vm/drop_caches 觸發緩存失效,觀察 RT 抖動。
軍規 37:jmap -histo:live 查看 Session 對象是否泄漏。
軍規 38:Arthas ognl 改 SystemProperty 做動態開關演練。
軍規 39:磁盤寫滿 touch bigfile,驗證 AccessLogValve 是否阻塞線程。
軍規 40:Chaos Mesh 注入 Pod CPU 100 %,驗證 readinessProbe 摘除流量。
(七)云原生與 CI/CD 7 條
軍規 41:Dockerfile 用 distroless/java17-base,鏡像 60 MB → 40 MB。
軍規 42:非 root 運行
RUN addgroup -g 1000 tomcat && adduser -D -s /bin/sh -u 1000 -G tomcat tomcat。
軍規 43:分層構建
依賴層 COPY pom.xml 單獨緩存,代碼變更后 5 s 構建完成。
軍規 44:Helm Chart
values.yaml 暴露 replicaCount、resources、jvmOpts,支持多環境。
軍規 45:優雅停機腳本
preStop: /bin/sh -c "sleep 15 && catalina.sh stop" 讓正在處理的請求完成。
軍規 46:HPA 雙指標
cpuUtilization=60% + tomcat_threadpool_currentThreadsBusy>80% 并發。
軍規 47:Keda 基于 Kafka 消息積壓自動擴容 Tomcat Pod。
結語
40 條軍規是 50 臺 Tomcat、200 次故障、3 個 P1 事故后的復盤。請把這份清單貼在 wiki 首頁,下次事故來臨前,你已經把風險提前清零。