首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 程式設計入門

Tomcat 目錄結構、核心配置與類載入機制深度解析

     編輯:Java 程式設計入門

Tomcat 目錄結構速覽

目錄/檔案用途關鍵說明
bin/啟動/關閉腳本startup.sh, shutdown.sh, catalina.sh, setenv.sh (自定義 JVM 參數)
conf/全域配置server.xml (核心), web.xml (預設 Servlet 映射), context.xml, tomcat-users.xml
lib/Tomcat 共享庫servlet-api.jar, jasper.jar, JDBC 驅動等,對所有 Webapp 可見
webapps/Web 應用部署目錄WAR 自動展開,ROOT/manager/host-manager 為內建應用
logs/日誌輸出catalina.out, localhost.yyyy-mm-dd.log, access_log
work/JSP 編譯產物JSP → Servlet .java/.class,清理可強制重新編譯
temp/暫存檔上傳大檔案緩衝等

Web 應用標準目錄結構 (Servlet Spec)

myapp.war (或解壓目錄 myapp/)
├── index.jsp, static/
├── WEB-INF/
│   ├── web.xml              (Servlet 3.0+ 可選,註解替代)
│   ├── classes/             (編譯後 .class,優先載入)
│   ├── lib/                 (應用私有 JAR,僅此 Webapp 可見)
│   └── tags/, tld/          (標籤庫)
└── META-INF/
    └── context.xml          (應用級 Context 配置)

核心配置檔詳解

server.xml — 容器骨架

<Server port="8005" shutdown="SHUTDOWN">
  <Listener className="org.apache.catalina.startup.VersionLoggerListener" />
  <GlobalNamingResources> ... </GlobalNamingResources>
  
  <Service name="Catalina">
    <!-- 連接器:HTTP/1.1, NIO, AJP -->
    <Connector port="8080" protocol="HTTP/1.1"
               connectionTimeout="20000"
               redirectPort="8443"
               maxThreads="200"
               acceptCount="100"
               compression="on"
               compressableMimeType="text/html,text/xml,application/json" />
    <Connector port="8009" protocol="AJP/1.3" redirectPort="8443" />
    
    <Engine name="Catalina" defaultHost="localhost">
      <Realm className="org.apache.catalina.realm.LockOutRealm">
        <Realm className="org.apache.catalina.realm.UserDatabaseRealm"
               resourceName="UserDatabase" />
      </Realm>
      
      <Host name="localhost" appBase="webapps"
            unpackWARs="true" autoDeploy="true">
        <Valve className="org.apache.catalina.valves.AccessLogValve"
               directory="logs" prefix="access_log" suffix=".log"
               pattern="%h %l %u %t "%r" %s %b" />
      </Host>
    </Engine>
  </Service>
</Server>

關鍵元素層級:Server → Service → Connector/Engine → Host → Context

web.xml — Servlet 容器預設配置

  • $CATALINA_HOME/conf/web.xml:全域預設 (DefaultServlet, JspServlet, session-config, mime-mapping)
  • WEB-INF/web.xml:應用覆蓋/擴充
  • Servlet 3.0+ 多用註解 (@WebServlet, @WebFilter, @WebListener) 替代

HTTP 請求處理流程 (以 https://localhost:8080/myapp/user/list 為例)

  1. Connector (port 8080) 接收請求,封裝 HttpServletRequest/Response
  2. Engine (Catalina) 根據 Host header 選擇 Host (localhost)
  3. Host 根據 context path (/myapp) 選擇 Context
  4. Context 在映射表尋找 /user/list → 對應 Servlet
  5. Servlet 執行 → 產生回應 → 逆向傳回 Connector → 客戶端

類載入器階層與委派模型

Bootstrap ClassLoader (JAVA_HOME/jre/lib/rt.jar)
    ▲
    │ 父優先委派
    ▼
System/Application ClassLoader (CLASSPATH)
    ▲
    │
    ▼
Common ClassLoader ($CATALINA_HOME/lib/*.jar)  ← Tomcat 內核 + 共享庫
    ▲
    │ 打破雙親委派 (子優先)
    ▼
Webapp ClassLoader (WEB-INF/classes → WEB-INF/lib/*.jar)  ← 每個 Webapp 隔離

關鍵規則

  1. WEB-INF/classes 優先於 WEB-INF/lib (同名類取 classes)
  2. Webapp 類載入器先找自己,再委派 Common (違背雙親委派,保證應用隔離)
  3. JSP 編譯類由 Jasper 載入,置於 work/,同樣走 Webapp ClassLoader
  4. 常見衝突:應用帶 servlet-api.jar → LinkageError → 移除,改用 provided scope

JVM 參數調優 (setenv.sh)

#!/bin/bash
export CATALINA_OPTS="
  -Xms2g -Xmx4g
  -XX:MetaspaceSize=256m -XX:MaxMetaspaceSize=512m
  -XX:+UseG1GC -XX:MaxGCPauseMillis=100
  -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=$CATALINA_HOME/logs
  -Djava.security.egd=file:/dev/./urandom
  -Dfile.encoding=UTF-8
  -Duser.timezone=Asia/Taipei"
# Windows 用 setenv.bat,語法調整為 set CATALINA_OPTS=...

常見部署問題排查

❌ 404 Not Found → 檢查 webapps/ 下是否有對應目錄/WAR,server.xml Host appBase 是否正確

❌ ClassNotFound / NoClassDefFound → 類載入器衝突,檢查 WEB-INF/lib 是否重複/缺漏

❌ 埠口佔用 → netstat -anp | grep 8080,修改 server.xml Connector port

❌ 中文亂碼 → URIEncoding="UTF-8" 加在 Connector,確保 DB/檔案編碼一致

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved