说说war和jar的区别
# 说说 war 和 jar 的区别
WAR
(Web Application Archive)和 JAR
(Java Archive)是 Java 生态中两种常见的归档文件格式,它们的核心区别在于用途、结构和部署场景。以下是详细对比:
# 一、核心定义
JAR(Java Archive)
- 用途:通用的 Java 归档文件,用于打包 Java 类文件(
.class
)、资源文件(如图片、配置文件)、元数据(MANIFEST.MF
)以及依赖库。 - 典型场景:
- 作为库(如 Spring 框架的依赖包)。
- 打包独立的 Java 应用程序(通过
MANIFEST.MF
指定入口类)。 - 用于构建可执行的 Java 程序(如
java -jar app.jar
)。
- 用途:通用的 Java 归档文件,用于打包 Java 类文件(
WAR(Web Application Archive)
- 用途:专为 Java Web 应用设计的归档文件,包含 Web 应用的所有内容(如 JSP、HTML、Servlet 类、配置文件等),需部署在 Servlet 容器(如 Tomcat、Jetty)中运行。
- 典型场景:
- 传统 Java Web 项目的部署(如 Spring MVC 应用)。
- 需要动态生成网页或提供 HTTP 接口的服务。
# 二、结构差异
目录结构 | JAR | WAR |
---|---|---|
根目录 | 任意结构(无强制要求) | 固定结构(符合 Java Web 规范) |
配置文件 | META-INF/MANIFEST.MF | WEB-INF/web.xml (核心配置) |
资源存放 | 资源文件可直接放在任意目录 | 静态资源(HTML/CSS/JS)需放在 Web 根目录下,动态资源(如JSP)放在特定位置 |
依赖管理 | 依赖的 JAR 包需显式引用 | 依赖的 JAR 包需放在 WEB-INF/lib 目录下 |
入口类 | 通过 MANIFEST.MF 指定主类 | 无需指定入口类,由 Servlet 容器启动 |
示例对比:
JAR 结构:
myapp.jar ├── com/example/Main.class ├── config.properties └── META-INF/ └── MANIFEST.MF (Main-Class: com.example.Main)
1
2
3
4
5WAR 结构:
mywebapp.war ├── index.html ├── WEB-INF/ │ ├── web.xml // Web应用配置 │ ├── classes/ // 编译后的类文件 │ └── lib/ // 依赖的JAR包 └── static/ // 静态资源
1
2
3
4
5
6
7
# 三、执行方式
- JAR:
- 可直接运行:
java -jar app.jar
(需在MANIFEST.MF
中指定主类)。 - 作为库被其他项目引用(如 Maven 依赖)。
- 可直接运行:
- WAR:
- 必须部署到 Servlet 容器(如 Tomcat)中运行。
- 容器启动时加载
web.xml
并初始化 Servlet、过滤器等组件。
# 四、适用场景对比
场景 | 推荐格式 | 原因 |
---|---|---|
开发通用库或工具类 | JAR | 灵活、轻量,适合跨项目复用 |
构建独立的 Java 应用程序 | JAR | 可直接运行,无需依赖外部容器 |
传统 Web 应用(如 Spring MVC) | WAR | 需要 Servlet 容器支持,符合 Java EE 规范 |
Spring Boot 嵌入式 Web 应用 | JAR | 内置 Tomcat/Undertow,无需外部容器,简化部署 |
# 五、Spring Boot中的特殊性
在Spring Boot中,JAR
和 WAR
的界限变得模糊:
可执行 JAR:
- 使用
spring-boot-maven-plugin
打包,内嵌 Tomcat 等容器。 - 结构包含:
BOOT-INF/classes/
(应用类)、BOOT-INF/lib/
(依赖库)、META-INF/MANIFEST.MF
。 - 直接运行:
java -jar springboot-app.jar
。
- 使用
WAR:
- 需继承
SpringBootServletInitializer
以兼容外部容器。 - 部署到传统 Servlet 容器(如 Tomcat 8+)。
- 需继承
# 六、常见问题
为什么有些 JAR 不能直接运行
- 缺少
Main-Class
配置(MANIFEST.MF
中未指定入口类)。 - 解决方法:通过构建工具(如 Maven/Gradle)配置主类。
- 缺少
WAR 能否脱离 Servlet 容器运行?
- 不能,必须依赖 Tomcat/Jetty 等容器。
JAR 和 WAR 能否互相转换?
- 可手动调整结构和配置文件,但需符合目标格式规范。
# 总结
- JAR:通用性更强,适合库、独立应用或嵌入式服务(如 Spring Boot)。
- WAR:专为 Web 应用设计,需依赖 Servlet 容器,结构更严格。
选择时需结合项目类型和部署环境:
- 快速启动或微服务场景 → 优先使用 可执行 JAR(如 Spring Boot)。
- 传统企业项目或需共享容器资源 → 使用 WAR。
上次更新: 2025/5/30 17:49:49