背景

本文是《JavaEE 后端从小白到大神》修仙系列第一篇,正式进入JavaEE后端世界,本篇文章主要聊JavaEE。若想详细学习请点击首篇博文,我们开始把。

第一篇:JavaEE 概述与体系总览

理解 JavaEE 的本质、历史演进(J2EE → JavaEE → Jakarta EE)、核心规范与运行机制。

  • 什么是 JavaEE(Jakarta EE);
  • 与 JavaSE 的区别;
  • JavaEE 的核心规范列表(Servlet、JSP、JPA、EJB、JMS、JAX-RS、CDI、JSF 等);
  • 应用服务器与 Web 容器区别;
  • JavaEE 的架构层次:表示层、业务层、持久层;
  • JavaEE 的运行机制与依赖注入模型。

1. 什么是 JavaEE(Jakarta EE)

JavaEE 是 Java 生态中专门为 “企业级后端应用” 设计的技术体系,其核心目标是解决 “大规模、高可用、分布式” 的后端业务需求。

1.1 JavaEE 的历史演进

“JavaEE” 和 “Jakarta EE” 的关系 —— 其实二者是同一技术体系的不同阶段,核心规范完全一致,只是因所有权变更换了名字:

  • J2EE(2001-2006):最初叫“Java 2 Platform, Enterprise Edition”,是 Sun 公司为企业级开发推出的标准,这是 JavaEE 的“1.0 时代”;
  • JavaEE(2006-2017):Sun 公司简化命名为“Java Platform, Enterprise Edition”,期间逐步完善规范(如加入 JPA、JAX-RS 等),成为企业级后端的主流技术栈;
  • Jakarta EE(2017-至今):2017 年 Oracle 将 JavaEE 所有权转让给 Eclipse 基金会,因商标版权问题更名为“Jakarta EE”,但核心规范(如 Servlet、JSP)和技术方向完全不变,目前最新版本为 Jakarta EE 11。

1.2 JavaEE 的本质

JavaEE 的本质:“规范集合” 而非 “具体实现”。

需要特别注意:JavaEE 不是某一个 “工具” 或 “框架”,而是一套 “技术规范文档”—— 它定义了后端开发需要具备的核心能力(比如 “如何处理 HTTP 请求”“如何操作数据库”),但不提供具体代码实现。

真正的“实现”由第三方厂商提供,比如:

  • Web 容器(实现 Servlet/JSP 规范):Tomcat、Jetty;
  • 应用服务器(实现全套 Jakarta EE 规范):WildFly(原 JBoss)、GlassFish;
  • 持久层框架(实现 JPA 规范):Hibernate、EclipseLink。

2. JavaEE 与 JavaSE 的区别

Java 生态分为 SE、EE、ME 三大体系(ME 已逐步淘汰),其中 JavaSE 是基础,JavaEE 是在 SE 之上的“企业级扩展”,二者的关系就像“地基”与“高楼”:

对比维度 JavaSE(Standard Edition) JavaEE(Enterprise Edition)
核心定位 Java 基础平台,提供通用编程能力 企业级后端平台,专注后端业务场景
包含内容 基础语法(变量、循环、面向对象)、集合(List/Map)、IO、多线程、基础网络编程等 在 SE 基础上,增加 Servlet、JSP、JPA、EJB 等“后端专属规范”
应用场景 桌面应用(如 Swing 程序)、工具开发(如命令行工具)、后端开发的“基础支撑” 网站后台、API 服务、分布式系统(银行、电商、政务系统等)
依赖关系 独立运行,不依赖其他 Java 体系 完全依赖 JavaSE,是 SE 的“超集”(必须先掌握 SE 才能学 EE)

举个实际例子:
当你用 Java 写一个“读取本地文件并统计字数”的程序时,只用 JavaSE 的 IO 包即可;但当你要写一个“接收前端登录请求、查询数据库并返回结果”的后端接口时,就需要用到 JavaEE 的 Servlet(处理 HTTP 请求)和 JPA(操作数据库)规范——这就是二者的核心区别。

3. JavaEE 的核心规范列表

JavaEE 包含十余种规范,覆盖了后端开发的全链路需求(从请求处理到数据存储,再到分布式支撑)。对新手而言,无需一次性掌握所有规范,重点先学“高频核心规范”:

规范名称 英文全称 核心作用 学习优先级
Servlet Java Servlet 处理前端 HTTP 请求(如接收参数、返回响应),是 JavaEE Web 开发的“基石” ★★★★★
JSP JavaServer Pages 动态生成 HTML 页面(现已逐步被前后端分离替代,但老项目仍在使用) ★★★☆☆
JPA Java Persistence API 面向对象的数据库操作规范(无需手写 JDBC 代码,用“类”操作“表”) ★★★★★
JAX-RS Java API for RESTful Web Services 开发 RESTful API 的规范(如定义 GET/POST 接口、返回 JSON 数据) ★★★★★
CDI Contexts and Dependency Injection 依赖注入规范(管理对象创建与依赖,简化代码耦合) ★★★★☆
EJB Enterprise JavaBean 封装复杂业务逻辑(如分布式事务、高并发处理),主要用于大型企业系统 ★★★☆☆
JMS Java Message Service 消息队列规范(实现系统间异步通信,如订单创建后异步发送短信) ★★★☆☆
JTA Java Transaction API 分布式事务规范(保证多数据库操作的一致性,如转账时“扣款”和“到账”必须同时成功) ★★★☆☆

4. 应用服务器与 Web 容器区别

很多同学会把 “应用服务器” 和 “Web 容器” 混为一谈,其实二者的核心区别在于 “支持的 JavaEE 规范范围”:

4.1 核心定义

  • Web 容器(Web Container):仅支持 JavaEE 中的“Web 层规范”(主要是 Servlet 和 JSP),功能相对轻量,适合开发简单 Web 应用或前后端分离的 API 服务;

  • 应用服务器(Application Server):支持 全套 Jakarta EE 规范(包括 Web 层、业务层、持久层等所有规范),功能强大,适合开发大型企业级应用(如需要分布式事务、消息队列的系统)。

4.2 常见产品对比

类型 代表产品 支持规范范围 适用场景
Web 容器 Tomcat、Jetty 仅支持 Servlet、JSP 等 Web 层规范 中小型 Web 应用、前后端分离 API 服务、开发环境测试
应用服务器 WildFly(原 JBoss)、GlassFish、WebLogic 支持全套 Jakarta EE 规范(Servlet/JPA/EJB/JMS 等) 大型企业系统(银行、电商、政务平台)

5. JavaEE 的架构层次

JavaEE 推荐采用 “分层架构” 开发后端应用,核心目的是 “解耦代码”—— 让不同功能的代码放在不同层级,便于维护和扩展。经典的 JavaEE 分层架构分为 3 层:

5.1 三层架构核心划分

graph TD
    前端 -->|1. 发请求| 表示层
    表示层 -->|2. 传参数| 业务层
    业务层 -->|3. 调接口| 持久层
    持久层 -->|4. 查数据| 数据库
    数据库 -->|5. 返数据| 持久层
    持久层 -->|6. 返结果| 业务层
    业务层 -->|7. 返结果| 表示层
    表示层 -->|8. 返响应| 前端
  1. 表示层(Presentation Layer)

    • 作用:接收前端请求,返回处理结果(相当于后端的“入口和出口”);
    • 技术实现:Servlet(处理 HTTP 请求)、JAX-RS(提供 REST API)、JSP(动态页面,已逐步淘汰);
    • 代码职责:仅做“请求参数校验”和“响应格式封装”,不处理复杂业务逻辑(比如判断请求参数是否为空,将结果封装为 JSON 返回)。
  2. 业务层(Business Layer)

    • 作用:封装核心业务逻辑(后端系统的“大脑”);
    • 技术实现:CDI(管理业务对象)、EJB(复杂业务场景);
    • 代码职责:处理业务规则(比如“用户登录时校验密码是否正确”“计算订单金额时叠加优惠”),调用持久层操作数据库。
  3. 持久层(Persistence Layer)

    • 作用:与数据库交互(后端的“数据管家”);
    • 技术实现:JPA(主流)、JDBC(底层,规范未直接定义,但属于基础);
    • 代码职责:仅做“数据的增删改查”(比如“根据用户 ID 查询用户信息”“保存订单数据到数据库”),不包含业务逻辑。

5.2 分层架构的优势

  • 解耦:比如要修改“数据库操作方式”(从 MySQL 换成 Oracle),只需修改持久层代码,业务层和表示层无需变动;
  • 易维护:不同层级的代码职责明确,出问题时能快速定位(比如前端请求报错,先查表示层;数据查询错误,先查持久层);
  • 可复用:比如“用户信息查询”的逻辑放在持久层,业务层的“登录”“个人中心”功能都能复用该逻辑。

6. JavaEE 的运行机制与依赖注入模型

在分层架构中,业务层(Service)需要调用持久层(Repository)的方法——这就产生了“依赖关系”(Service 依赖 Repository)。JavaEE 用“依赖注入”(DI)解决这个问题,核心是“容器自动将依赖对象注入到需要的地方”。

举个例子(基于 CDI 规范):

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
// 1. 持久层:定义一个操作用户数据的 Repository
@Repository // 标记这是一个“持久层对象”,让容器管理
public class UserRepository {
    public User findById(Long id) {
        // 用 JPA 查询数据库,返回用户信息
        return jpaEntityManager.find(User.class, id);
    }
}

// 2. 业务层:Service 依赖 Repository
@Service // 标记这是一个“业务层对象”,让容器管理
public class UserService {
    // 3. 依赖注入:容器自动将 UserRepository 对象注入到这里,无需手动 new
    @Inject
    private UserRepository userRepository;

    // 业务方法:调用 Repository 的方法
    public User getUserById(Long id) {
        return userRepository.findById(id); // 直接使用注入的对象
    }
}

7. JavaEE 体系总结

7.1 JavaEE 架构层次图

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
┌─────────────────────────────────────────────────────────────────┐
│                      客户端层(Client Tier)                     │
│  ┌──────────┐  ┌──────────┐  ┌──────────┐  ┌────────────────┐  │
│  │ Web浏览器 │  │ 移动应用  │  │ 桌面应用  │  │ 其他服务调用者  │  │
│  └──────────┘  └──────────┘  └──────────┘  └────────────────┘  │
└───────────────────────────────────┬─────────────────────────────┘
┌───────────────────────────────────▼─────────────────────────────┐
│                      表示层(Presentation Tier)                 │
│  ┌──────────┐  ┌──────────┐  ┌──────────┐  ┌────────────────┐  │
│  │  Servlet  │  │   JSP    │  │   JSF    │  │   JAX-RS       │  │
│  └──────────┘  └──────────┘  └──────────┘  └────────────────┘  │
└───────────────────────────────────┬─────────────────────────────┘
┌───────────────────────────────────▼─────────────────────────────┐
│                      业务层(Business Tier)                     │
│  ┌──────────┐  ┌──────────┐  ┌──────────┐  ┌────────────────┐  │
│  │   EJB    │  │   CDI    │  │   JMS    │  │   事务管理      │  │
│  └──────────┘  └──────────┘  └──────────┘  └────────────────┘  │
└───────────────────────────────────┬─────────────────────────────┘
┌───────────────────────────────────▼─────────────────────────────┐
│                      持久层(Persistence Tier)                  │
│  ┌──────────┐  ┌──────────┐  ┌────────────────────────────────┐ │
│  │   JPA    │  │ JDBC API │  │  数据库(MySQL/Oracle等)      │ │
│  └──────────┘  └──────────┘  └────────────────────────────────┘ │
└─────────────────────────────────────────────────────────────────┘

7.2 JavaEE 每个组件职责

核心组件职责

  1. 客户端层

    • 负责与用户交互或发起服务请求,不包含业务逻辑。
    • 例如:Web浏览器(通过HTTP访问)、移动App(通过API调用)、桌面应用(通过RMI等)。
  2. 表示层

    • 处理客户端请求,返回响应(如HTML、JSON),负责请求分发和数据展示。
    • Servlet:Java类,处理HTTP请求(GET/POST),生成动态内容。
    • JSP:嵌入Java代码的HTML页面,简化动态页面开发(最终编译为Servlet)。
    • JSF:组件化Web框架,通过UI组件(按钮、表单)构建页面,支持事件驱动。
    • JAX-RS:RESTful API规范,用于开发HTTP接口(如JSON/XML接口)。
  3. 业务层

    • 封装核心业务逻辑,处理事务、安全、并发等非功能性需求。
    • EJB(企业JavaBean):服务器端组件,提供分布式事务、远程调用等企业级功能(分会话Bean、实体Bean、消息驱动Bean)。
    • CDI(上下文和依赖注入):管理组件生命周期和依赖注入,简化组件协作。上下文就是 Bean 存在的 “时间和范围”。
    • JMS(Java消息服务):实现异步通信,支持点对点或发布订阅模式的消息传递。
    • 事务管理:通过JTA(Java事务API)保证分布式事务的ACID特性。
  4. 持久层

    • 负责数据存储与读取,将内存中的对象与数据库关联。
    • JPA(Java持久化API):ORM规范,通过注解/XML映射对象与数据库表,简化CRUD操作(实现框架如Hibernate)。
    • JDBC:底层数据库访问API,直接操作SQL语句(JPA基于JDBC封装)。

7.3 JavaEE 与 Spring 体系的关系与差异

7.3.1 关系

  • 互补性:Spring 最初是为解决 JavaEE 中 EJB 过重的问题而诞生,早期以“轻量级替代 EJB”为目标,后来逐渐扩展为覆盖 JavaEE 大部分功能的生态。

  • 兼容性:Spring 可以运行在 JavaEE 应用服务器(如 WildFly)中,且支持 JavaEE 规范(如 JPA、Servlet、JMS 等),例如 Spring Data JPA 是对 JPA 的封装。

  • 演进影响:Jakarta EE(JavaEE 更名后)后期也借鉴了 Spring 的理念(如简化配置、强调注解),例如 CDI 规范与 Spring 的依赖注入思想相似。

7.3.2 差异

维度 JavaEE(Jakarta EE) Spring 体系
定位 企业级应用开发的规范集合(由 Eclipse 基金会维护) 企业级应用开发的框架生态(由 Pivotal 维护)
实现方式 规范由第三方厂商实现(如 WildFly 实现 EJB、Servlet) 框架自身提供实现(如 Spring Core、Spring MVC 等)
重量级 vs 轻量 早期依赖重型应用服务器(如 WebLogic),后期轻量化 从设计之初就强调轻量,可运行在普通 Web 容器(如 Tomcat)
核心思想 基于“规范”,强调标准化和跨厂商兼容性 基于“约定优于配置”,强调灵活性和开发效率
组件模型 依赖 EJB、CDI 等组件模型,规范严格 基于 IoC 容器和 Bean,组件模型更灵活(无严格规范)
生态覆盖 覆盖传统企业级场景(分布式事务、消息队列等) 覆盖更广泛(微服务、云原生、大数据等,如 Spring Boot/Cloud)
学习成本 需理解众多规范细节,学习曲线较陡 文档丰富、工具链成熟(如 Spring Boot 自动配置),入门简单

依赖注入的优势:

  • 解耦:Service 不需要知道 Repository 的创建细节(比如是否需要配置数据库连接),只需关注“如何调用”;
  • 便于测试:测试时可以用“模拟对象”替换真实的 Repository,无需依赖数据库。

结语

JavaEE 是一套标准化的企业级开发规范,强调跨平台兼容性;Spring 是一套更灵活的框架生态,简化了开发流程并扩展到更多场景。两者从早期的“替代关系”逐渐演变为“互补关系”,实际开发中常结合使用(如 Spring 集成 JPA、Servlet)。