Spring Boot打出的jar包为什么可以独立运行

闲来无事,浏览网页看到有人说jar包为什么可以独立运行,想起前端时间写的jar打包后无法正常运行处理。jar解压缩后有多个文件夹,内部存放运行所需jar包和一些配置文件,本文做一个简单介绍。

JAR包和WAR包区别

在Java开发中,JAR(Java ARchive)包和WAR(Web Application ARchive)包都是用来打包文件和资源的归档文件,但它们的用途和内容有所不同。

1. 用途

  • JAR包:通常用于存储Java类文件、与应用程序相关的元数据和资源(如文本、图片等)。JAR包可以作为库被其他应用程序依赖,或者包含可执行的Java应用程序。
  • WAR包:专门用于分发Java Web应用程序。它包含Servlet、JSP、HTML、JavaScript、CSS等Web应用所需的所有组件。

2. 结构

  • JAR包:可以包含任意的文件和文件夹,通常包含一个META-INF目录,里面包含了MANIFEST.MF文件,这个文件定义了包的版本、主类等信息。
  • WAR包:具有特定的目录结构,必须包含一个WEB-INF文件夹,其中包含web.xml(描述了Web应用的结构和内容)、应用程序库(/WEB-INF/lib目录下的JAR文件)和类文件(/WEB-INF/classes目录)。

3. 使用场景

  • JAR包:适用于任何Java应用,无论是桌面应用还是服务器端应用。
  • WAR包:仅用于Web应用服务器如Tomcat、Jetty等,用于部署Web应用。

4. 执行

  • JAR包:如果包含主类,可以直接通过java -jar命令运行。
  • WAR包:需要部署到支持Servlet和JSP的Web服务器或应用服务器上,不能直接运行。

JAR包和WAR包都是Java环境中用于打包文件的格式,但JAR包更通用,而WAR包专门用于Web应用的分发和部署。

解压缩后文件目录

JAR 包结构示例

myapp.jar
├── META-INF
│   ├── MANIFEST.MF
│   └── ...
├── com
│   └── example
│       ├── Main.class
│       ├── utils
│       │   ├── Helper.class
│       │   └── Constants.class
│       └── services
│           ├── UserService.class
│           └── ProductService.class
└── resources
    ├── config.properties
    └── messages.properties

各个文件夹功能

1.META-INF:
  • MANIFEST.MF: 这个文件包含关于 JAR 包的元数据,比如版本信息、主类(Main-Class)等。可以在这里指定程序的入口点。
Manifest-Version: 1.0
Main-Class: com.example.Main
Class-Path: lib/dependency1.jar lib/dependency2.jar
Implementation-Title: My Application
Implementation-Version: 1.0.0
Implementation-Vendor: Example Corp
常见属性及功能解释:

Manifest-Version:

  • 功能: 指定清单文件的版本。通常是1.0
  • 示例: Manifest-Version: 1.0

Main-Class:

  • 功能: 指定JAR文件的主类,即包含public static void main(String[] args)方法的类。当使用java -jar命令运行JAR文件时,Java虚拟机(JVM)会从这个类开始执行。
  • 示例: Main-Class: com.example.Main

Class-Path:

  • 功能: 指定运行时类路径。如果JAR文件依赖于其他JAR文件,可以在此处列出这些依赖。路径可以是相对路径或绝对路径。
  • 示例: Class-Path: lib/dependency1.jar lib/dependency2.jar

Implementation-Title:

  • 功能: 指定JAR文件的标题或名称。通常用于标识应用程序的名称。
  • 示例: Implementation-Title: My Application

Implementation-Version:

  • 功能: 指定JAR文件的版本。通常用于标识应用程序的版本号。
  • 示例: Implementation-Version: 1.0.0

Implementation-Vendor:

  • 功能: 指定JAR文件的供应商或开发者。通常用于标识开发该应用程序的公司或个人。
  • 示例: Implementation-Vendor: Example Corp
2.com/example:
  • Main.class: 主类,程序的入口点。通常包含 public static void main(String[] args) 方法。
  • utils: 实用工具类文件夹。
    • Helper.class: 一些辅助方法,可能用于日志记录、数据处理等。
    • Constants.class: 常量定义类,存储全局常量。
  • services: 业务逻辑类文件夹。
    • UserService.class: 用户相关的服务类,可能包含用户注册、登录等方法。
    • ProductService.class: 产品相关的服务类,可能包含产品查询、添加等方法。
3.resources:
  • config.properties: 配置文件,存储应用程序的配置信息,比如数据库连接、API 密钥等。
  • messages.properties: 国际化消息文件,存储应用程序中的文本信息,用于多语言支持。

为什么可以独立运行

Spring Boot 允许创建可独立运行的 JAR 文件,这种 JAR 文件被称为 “可执行 JAR” 或 “fat JAR”(有时也称为 “uber JAR”)。这种 JAR 文件包含了所有必要的依赖库、类文件和资源,使得应用可以通过一个简单的 java -jar 命令运行,而无需额外的类路径设置。这是通过以下几个关键的配置和技术实现的:

1. 内嵌容器

Spring Boot 应用通常内嵌一个 Web 服务器(如 Tomcat、Jetty 或 Undertow),这意味着不需要部署到外部服务器。应用启动时,内嵌的 Web 服务器也会被启动,从而处理 HTTP 请求。

2. Spring Boot Starter

Spring Boot 使用一系列的 “starters” 来简化依赖管理。这些 starters 负责将应用所需的依赖库自动包含在最终的 JAR 文件中。例如,spring-boot-starter-web 会添加 Tomcat 和 Spring MVC 的依赖。

3. Spring Boot Maven 插件

这些插件负责构建过程中的重要任务,如打包应用和依赖项。特别是,它们会创建一个包含所有依赖的 JAR 文件,并且配置好 META-INF/MANIFEST.MF 文件,使其指向一个特殊的类加载器,这个类加载器能够从 JAR 文件内部加载类和资源。

4. 类加载器

Spring Boot 使用自定义的类加载器来从 JAR 文件内部的嵌套 JAR 文件中加载类。这意味着,尽管所有的库都被打包在一个单一的 JAR 文件中,Spring Boot 仍然能够从这些库中加载类。

5. MANIFEST.MF 配置

META-INF/MANIFEST.MF 文件中,Spring Boot 配置了 Main-Class 属性,该属性指向了 org.springframework.boot.loader.JarLauncher。这是一个特殊的启动器,负责初始化 Spring Boot 应用。此外,还有 Start-Class 属性,它指定了包含 main 方法的实际入口类。

示例:MANIFEST.MF 中的关键配置

Main-Class: org.springframework.boot.loader.JarLauncher
Start-Class: com.example.MyApplication

这种配置方式使得 Spring Boot 应用可以作为一个独立程序运行,而不需要任何外部依赖,除了 Java 运行时环境。这极大地简化了部署和分发过程,使得开发者可以轻松地在不同环境中部署和运行他们的应用。

  • 33
    点赞
  • 28
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

懒人w

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值