jsp:plugin 是 JSP 1.1 引入的標準動作標籤,用於自動產生 <OBJECT> (IE) 或 <EMBED> (Netscape) 標籤,讓瀏覽器下載並執行 Java Applet 或 JavaBean 元件。隨著瀏覽器廠商停止支援 NPAPI 外掛架構 (Chrome 45+、Firefox 52+、Edge 全版本)、Java 官方淘汰 Applet (JDK 9 標記移除、JDK 11 徹底移除)、現代 Web 技術 (WebAssembly、WebGL、PWA) 取代,此標籤已完全失去實用價值。本文作為歷史技術檔案保存,並提供現代遷移路徑。
| 時期 | 狀態 |
|---|---|
| 1995-2005 | Applet 盛行:跨平台豐富客戶端首選,銀行、證券、政府系統大量採用 |
| 2005-2015 | 衰退期:Flash/Flex、Silverlight、JavaScript/AJAX 崛起,安全性問題頻發 |
| 2015-2017 | 瀏覽器廠商宣布淘汰 NPAPI:Chrome 45 (2015/9)、Firefox 52 (2017/3) |
| 2017-2018 | Oracle 宣布 Java Applet 棄用:JDK 9 (2017/9) 標記 @Deprecated |
| 2018+ | 徹底終結:JDK 11 (2018/9) 移除 Applet API、瀏覽器無法載入 |
<jsp:plugin
type="bean|applet" <-- 必填:元件類型
code="ClassFileName.class" <-- 必填:主類別檔案名 (含 .class)
codebase="ClassFileDirectory" <-- 必填:類別檔目錄或 URL 路徑
name="instanceName" <-- 選填:實例名稱,供同頁多 Applet 通訊
archive="jar1.jar,jar2.jar" <-- 選填:JAR 檔列表,預先載入提升效能
align="bottom|top|middle|left|right" <-- 選填:對齊方式
height="displayPixels" <-- 選填:顯示高度
width="displayPixels" <-- 選填:顯示寬度
hspace="leftRightPixels" <-- 選填:水平間距
vspace="topBottomPixels" <-- 選填:垂直間距
jreversion="1.1|1.2|..." <-- 選填:最低 JRE 版本 (預設 1.1)
nspluginurl="URLToPlugin" <-- 選填:Netscape 外掛下載點
iepluginurl="URLToPlugin" <-- 選填:IE ActiveX 下載點
>
<jsp:params>
<jsp:param name="paramName" value="paramValue" />+
</jsp:params>
<jsp:fallback>
無法載入 Applet 的替代內容 (文字/圖片/連結)
</jsp:fallback>
</jsp:plugin>
<jsp:plugin
type="applet"
code="Molecule.class"
codebase="/html/applets"
width="400"
height="300"
jreversion="1.6"
archive="chemistry.jar,vecmath.jar"
nspluginurl="https://java.sun.com/products/plugin/1.6/jinstall-6u-windows-i586.cab"
iepluginurl="https://java.sun.com/products/plugin/1.6/jinstall-6u-windows-i586.cab"
>
<jsp:params>
<jsp:param name="molecule" value="molecules/benzene.mol" />
<jsp:param name="background" value="white" />
</jsp:params>
<jsp:fallback>
<p>您的瀏覽器不支援 Java Applet。</p>
<p><a href="https://java.com/download/">點此下載 Java Runtime</a></p>
<p>或查看靜態圖片:<img src="benzene.png" alt="苯分子結構"></p>
</jsp:fallback>
</jsp:plugin>
<!-- IE (ActiveX) -->
<OBJECT
classid="clsid:8AD9C840-044E-11D1-B3E9-00805F499D93"
codebase="https://java.sun.com/products/plugin/1.6/jinstall-6u-windows-i586.cab"
width="400" height="300"
name="moleculeApplet"
>
<PARAM name="code" value="Molecule.class" />
<PARAM name="codebase" value="/html/applets" />
<PARAM name="archive" value="chemistry.jar,vecmath.jar" />
<PARAM name="molecule" value="molecules/benzene.mol" />
<PARAM name="background" value="white" />
<PARAM name="type" value="application/x-java-applet;version=1.6" />
<COMMENT>
<EMBED
type="application/x-java-applet;version=1.6"
pluginspage="https://java.sun.com/products/plugin/1.6/jinstall-6u-windows-i586.cab"
code="Molecule.class"
codebase="/html/applets"
archive="chemistry.jar,vecmath.jar"
width="400" height="300"
molecule="molecules/benzene.mol"
background="white"
>
<NOEMBED>
無法載入 Applet...
</NOEMBED>
</COMMENT>
</OBJECT>
| 語法 | 用途 | 範例 |
|---|---|---|
<%-- ... --%> | JSP 註解 (不輸出到瀏覽器) | <%-- 伺服器端邏輯說明 --%> |
<!-- ... --> | HTML 註解 (輸出到瀏覽器) | <!-- 頁面載入時間: <%= new Date() %> --> |
<\% | 模板文字中輸出 <% | <\% out.print("test"); %> → 顯示 <% out.print("test"); %> |
%\> | Scriptlet 中輸出 %> | out.print("100\%>"); → 顯示 100%> |
\' | 單引號屬性值中輸出單引號 | <jsp:setProperty name='a' value='it\'s ok' /> |
\" | 雙引號屬性值中輸出雙引號 | <jsp:setProperty name="a" value="say \"hi\"" /> |
\%> | 屬性值中輸出 %> | <jsp:setProperty name="a" value="100\%>" /> |
<\% | 屬性值中輸出 <% | <jsp:setProperty name="a" value="<\%test" /> |
| Applet 能力 | 現代 Web 技術替代方案 | 關鍵技術 |
|---|---|---|
| 跨平台豐富 UI | React/Vue/Svelte + CSS Grid/Flex + Web Components | Virtual DOM, Shadow DOM, CSS Houdini |
| 高效能圖形/遊戲 | WebGL / WebGPU / Three.js / Babylon.js | GPU 加速著色器管線 |
| 科學計算/密碼學 | WebAssembly (Rust/C++/Go 編譯) + Web Workers | WASM SIMD, pthreads, Reference Types |
| 本地檔案存取 | File System Access API / IndexedDB / OPFS | Origin Private File System |
| 硬體裝置存取 | WebUSB / WebHID / Web Serial / Web Bluetooth | 裝置權限模型 |
| 離線運行 | PWA (Service Worker + Cache API + Manifest) | Workbox, Background Sync |
| 跨語言程式碼重用 | WebAssembly (將 Java/Kotlin/Rust 編譯為 WASM) | TeaVM, JWebAssembly, CheerpJ |
# 使用 TeaVM (Java bytecode → WASM)
# Maven 配置
<plugin>
<groupId>org.teavm</groupId>
<artifactId>teavm-maven-plugin</artifactId>
<version>0.8.0</version>
<configuration>
<targetDirectory>${project.build.directory}/wasm</targetDirectory>
<mainClass>com.example.AppletMain</mainClass>
</configuration>
</plugin>
優點:保留 Java 業務邏輯、效能接近原生。缺點:需重寫 UI 層 (無 AWT/Swing)、部分 JDK API 不支援。
# 後端:Spring Boot REST Controller
@RestController
@RequestMapping("/api/molecule")
public class MoleculeController {
@GetMapping("/{id}")
public MoleculeData getMolecule(@PathVariable String id) {
return moleculeService.load(id); // 原 Applet 邏輯移至這裡
}
}
# 前端:React + Three.js 渲染分子結構
function MoleculeViewer({ moleculeId }) {
const [data, setData] = useState(null);
useEffect(() => {
fetch(`/api/molecule/${moleculeId}`).then(r => r.json()).then(setData);
}, [moleculeId]);
return ; // Three.js 渲染
}
<!-- HTML 頁面引入 CheerpJ -->
<script src="https://caching.leaningtech.com/cheerpj3.js"></script>
<script>
cheerpjInit().then(() => {
cheerpjRunJar("/applets/chemistry.jar", "/applets/", "com.example.MoleculeApplet");
});
</script>
<canvas id="cheerpjCanvas" width="400" height="300"></canvas>
優點:零修改運行現有 Applet。缺點:商業授權、效能較原生差、檔案較大。
jsp:plugin 是 Web 歷史的見證者。它解決了 1990 年代跨瀏覽器 Java 部署的痛苦,但隨著 Web 標準演進 (HTML5、WebAssembly、PWA)、安全模型升級 (同源策略、CSP、權限模型)、瀏覽器架構重構 (多進程、站點隔離、移除 NPAPI),Java Applet 技術棧已徹底退出歷史舞台。
給維護舊系統的開發者:若系統仍依賴 Applet,請評估上述三條遷移路徑,制定 6-12 個月淘汰計畫。新專案絕對不要使用任何 Applet 相關技術。