WebLogic 提供 6 種 Session 持久化方式,其中 File 與 JDBC 為磁盤/數據庫落地模式,性能差異巨大。本文通過線程堆棧分析揭示 File 模式嚴重鎖競爭瓶頸,對比 JDBC 異步寫入優勢,給出生產環境配置建議與 CacheSize 調優指南。
| 類型 | 特點 | 性能 | 適用場景 |
|---|---|---|---|
| memory | 不持久化,僅內存 | 最高 | 單節點、可容忍 Session 丟失 |
| file | 序列化到本地文件 | 極低 (鎖競爭) | 開發/測試、極小流量 |
| jdbc | 存入數據庫表 wl_servlet_sessions | 高 (異步寫入) | 生產集群、高可用 |
| replicated | 內存 + 集群內複製 | 高 | 集群、小 Session、低延遲網路 |
| cookie | 客戶端 Cookie 存儲 | 中 (受限 4KB) | 無狀態、小數據 |
| replicated_if_clustered | 集群時 replicated,否則 memory | 自適應 | 混合部署 |
ArrayList<String> 10萬條)"ExecuteThread: '10'" waiting for monitor entry [0x03a2f000]
at weblogic.servlet.internal.session.FileSessionContext.loadSession(FileSessionContext.java:482)
- waiting to lock <0x159a82a8> (a java.lang.Object)
at weblogic.servlet.internal.session.FileSessionContext.sync(FileSessionContext.java:368)
- locked <0x159a82a8> (a java.lang.Object)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1052)
所有線程阻塞在同一把鎖 0x159a82a8 (FileSessionContext 實例),串行讀寫文件。
// FileSessionContext.sync(HttpSession sess) - 同步方法/塊鎖住整個 Context
synchronized (dirTreeLock) { // 全局鎖!
makeStorageDir(id);
os = new DataOutputStream(new FileOutputStream(saveTo));
WLObjectOutputStream oos = new WLObjectOutputStream(os);
oos.writeObject(data); // 序列化大對象,長時間持有鎖
...
}
設計錯誤:本應由每個 FileSessionData (對應單個 Session) 並行完成文件讀寫,卻集中在 FileSessionContext (管理器) 單線程串行執行。類比:50 個工人 (Session) 干活,老板 (Context) 包辦所有工作,串行完成 → 效率極低。
JDBCSessionData 直接操作數據庫,**無全局鎖**,各 Session 並行提交。PersistentStorePool) 提供多連接並行寫入能力。<session-descriptor>
<session-param>
<param-name>PersistentStoreType</param-name>
<param-value>jdbc</param-value>
</session-param>
<session-param>
<param-name>PersistentStorePool</param-name>
<param-value>SessionPool</param-value> <!-- 預建 JDBC 連接池 -->
</session-param>
<session-param>
<param-name>CacheSize</param-name>
<param-value>0</param-value> <!-- 見下文調優 -->
</session-param>
</session-descriptor>
在 SessionPool 連接的 Schema 下建表 wl_servlet_sessions (參考 WebLogic 文檔 sessions.html)。
| 值 | 行為 | 性能影響 |
|---|---|---|
| 0 (默認) | 請求結束從引用池移除 → GC 回收 → 下次請求從持久層 Load | 頻繁 Load/Store,**性能極差** |
| >0 (如 100) | LRU 緩存熱 Session 在內存,請求結束放入緩存,滿則淘汰最舊 | **大幅減少 Load/Store,極力推薦** |
控制台顯示的 Session 數 = 持久層中未過期總數,**非內存中實際數量**。
FileSessionData,各 Session 並行文件 I/O (需修改 WebLogic 源碼/反射注入,風險高)。CacheSize 減少落地頻次。CacheSize > 0。SessionStoreWriteTime),異常升高時排查鎖競爭或 DB 慢查詢。