錯誤現象
SEVERE [ContainerBackgroundProcessor[StandardEngine[Catalina]]]
org.apache.catalina.startup.HostConfig.deployDescriptors Error waiting for multi-thread deployment
java.lang.InterruptedException
at java.util.concurrent.FutureTask.awaitDone(FutureTask.java:404)
...
現象:修改包名及相關配置後,Tomcat 啟動報 `InterruptedException`,部署線程超時/中斷。
根因分析
- 舊版本應用殘留在 `webapps` 目錄:Tomcat 自動部署檢測到舊 WAR/目錄,嘗試並行部署新舊版本,導致線程衝突/超時。
- 配置文件包名未同步更新:`web.xml`、`spring-mvc.xml`、`context.xml`、註解掃描路徑 (`base-package`) 中的舊包名未改全,導致掃描失敗/死循環。
- IDE 緩存/編譯產物未清理:Eclipse/IDEA `target`/`build` 目錄殘留舊類文件,熱部署衝突。
解決步驟(按順序執行)
1. 徹底清理部署目錄(最關鍵)
# 停止 Tomcat
# 刪除 webapps 下項目相關所有文件
rm -rf $CATALINA_HOME/webapps/YourProject*
rm -rf $CATALINA_HOME/work/Catalina/localhost/YourProject*
# 清理 IDE 輸出目錄
# Eclipse: Project → Clean... → Clean all projects
# IDEA: Build → Rebuild Project / File → Invalidate Caches / Restart
2. 全局搜索替換包名
- Java 源碼:`package` 聲明、`import` 語句。
- 配置文件:
- `web.xml`:``、``、``、`` 中包名。
- Spring XML:`context:component-scan base-package="..."`、``、`aop:config` 表達式。
- Hibernate/MyBatis:`mapping` 資源路徑、實體類全限定名。
- `struts.xml` / `tiles.xml` 等。
- 註解掃描路徑:`@ComponentScan("new.package")`。
3. 重新構建並部署
# Maven 項目
mvn clean package -DskipTests
# 將生成的 WAR 複製到 webapps,或配置 Context 路徑
cp target/YourProject.war $CATALINA_HOME/webapps/
# 啟動 Tomcat
$CATALINA_HOME/bin/startup.sh
4. 驗證日志關鍵點
- `INFO: Deploying web application archive` → 部署開始。
- `INFO: Initializing Spring root WebApplicationContext` → Spring 啟動。
- 無 `SEVERE` / `ERROR` → 成功。
進階排查:若仍報 InterruptedException
- 檢查 `server.xml` `Host` 配置:`autoDeploy="true" deployOnStartup="true"` 可能導致並行部署衝突。臨時設為 `false` 手動部署驗證。
- 增加部署超時:`Host` 屬性 `deploymentTimeout="120"` (秒)。
- 檢查端口占用:`netstat -an | grep 8080`,確保無舊進程殘留。
- JVM 參數調整:`-Djava.util.concurrent.FutureTask.cancel=true` (罕見)。
避坑清單(修改包名必做)
| 文件/位置 | 檢查項 |
| Java 類 | package 行、import 行 |
| web.xml | servlet/filter/listener 全限定名 |
| Spring XML | component-scan、bean class、aop expression |
| 持久層配置 | entity/package、mapper 接口路徑 |
| 構建腳本 | maven-war-plugin、jar 包名 |
| 部署目錄 | 清空 webapps/work 相關舊文件 |
總結
修改包名後 Tomcat 報 `InterruptedException` 多因**舊部署殘留導致並行部署衝突**或**配置包名未全量同步**。**「清空 webapps/work → 全局替換包名 → Clean Rebuild → 重新部署」** 是標準解決流程。養成「修改包名即全局搜索、清理部署目錄」習慣,可避免 99% 此類啟動故障。
- 上一篇文章: Java 空指針異常排查:數組部分初始化導致後續元素為 null
- 下一篇文章: SQL 建表語句轉 C# 代碼:ADO.NET 參數化執行與實體類映射完整方案
Copyright ©
程式碼之家 All Rights Reserved