老司机教你用原生JDK 撸一个 MVC 框架!!!

时间:2023-03-09 03:32:01
老司机教你用原生JDK 撸一个 MVC 框架!!!

其实 Spring MVC 是一个基于请求驱动的 Web 框架,并且也使用了前端控制器模式来进行设计,再根据请求映射规则分发给相应的页面控制器进行处理,具体工作原理见下图。

老司机教你用原生JDK 撸一个 MVC 框架!!!

在这里,就不详细谈相关的原理和实现细节了,感兴趣的话,可以读一下这方面的书籍。

我在网上看到一篇不错的关于讲述怎么实现一个 MVC 框架的文章,在此,分享给各位读者,也许能帮助到你。

原文内容如下。

我今天主要带大家实现一个迷你版的 Spring MVC ,本项目将在一个干净的 web 工程开发,不引入 Spring,完全通过原生 JDK 来实现。

具体的工程代码结构如下图。

老司机教你用原生JDK 撸一个 MVC 框架!!!

相关代码说明:

  1. 在 annotation 包下,我将提供自定义的注解,为了方便理解,会与 Spring MVC 保持一致。
  2. 为了模拟 Spring MVC 的方法调用链,我这里提供 Controller/Service/Dao 层进行测试。
  3. 提供自定义的 DispatcherServlet 来完成核心逻辑处理。

一、自定义注解

先给各位读者解释一下 JDK 提供了几个元注解:

  • @Documented : JavaDoc文档
  • @Target:标志此注解可以修饰在哪些地方,类,成员变量,方法...
  • @Retention:Annotation的生命周期,一般情况下,我们自定义注解的话,显然需要在运行期获取注解的一些信息。

我这边自定义的注解主要是模拟 Spring MVC ,具体实现如下。

1、@Controller提供控制器

老司机教你用原生JDK 撸一个 MVC 框架!!!

2、@Qualifier提供依赖注入

老司机教你用原生JDK 撸一个 MVC 框架!!!

3、@RequestMapping提供URL地址处理映射

老司机教你用原生JDK 撸一个 MVC 框架!!!

4、Dao层注解

老司机教你用原生JDK 撸一个 MVC 框架!!!

5、Service层注解

老司机教你用原生JDK 撸一个 MVC 框架!!!

二、核心控制器

在 Spring MVC 中,DispatcherServlet 是核心类,下面我的代码主要用来实现它。首先来说,Spring MVC 中的 DispatcherServlet 说到底,还是 HttpServlet 的子类,因此我这边自定义的 DispatcherSerlvet 也需要继承 HttpServlet。

1、pom.xml 加入 servlet 依赖

老司机教你用原生JDK 撸一个 MVC 框架!!!

2、定义 DispatcherServlet

老司机教你用原生JDK 撸一个 MVC 框架!!!

代码中的 @WebServlet 用处是什么呢?其实,以前我们定义一个 Servlet ,需要在 web.xml 中去配置,不过在 Servlet 3.0 后出现了基于注解的 Servlet 。

仔细观察,你会发现,这个 DispatcherServlet 是自启动,而且传入了一个参数。

要知道,在 Spring MVC 中,要想基于注解,需要在配置中指明扫描的包路径,就像这个样子。

老司机教你用原生JDK 撸一个 MVC 框架!!!

为了方便,我这里就通过初始化参数直接将需要扫描的基包路径传入。

a、初始化流程

老司机教你用原生JDK 撸一个 MVC 框架!!!

其实,在 init 中,我们主要是完成了什么呢?

  • 我们应该去扫描基包下的类,得到信息 A。
  • 对于 @Controller/@Service/@Repository 注解而言,我们需要拿到对应的名称,并初始化它们修饰的类,形成映射关系 B。
  • 我们还得扫描类中的字段,如果发现有 @Qualifier 的话,我们需要完成注入。
  • 我们还需要扫描 @RequestMapping,完成 URL 到某一个 Controller 的某一个方法上的映射关系 C。

其实,Spring MVC 的处理流程,就是类似这样的!

b、扫描基包

老司机教你用原生JDK 撸一个 MVC 框架!!!

注意,基包是 X.Y.Z 的形式,而 URL 是 X/Y/Z 的形式,需要转换。

c、实例化

老司机教你用原生JDK 撸一个 MVC 框架!!!

从这里你可以看出,我们完成了被注解标注的类的实例化,以及和注解名称的映射。

d、依赖注入

老司机教你用原生JDK 撸一个 MVC 框架!!!

以前,我们总是说Spring IOC,上面不就是在做这个事情么?

e、URL映射处理

老司机教你用原生JDK 撸一个 MVC 框架!!!

我们需要把 URL 提取出来,映射到 Controller 的 Method 上。

f、doGet/doPost

老司机教你用原生JDK 撸一个 MVC 框架!!!

在 doPost 方法中,非常简单,我们只需要提取出 URL,通过 URL 映射到Method 上,然后通过反射的方式进行调用即可。

三、让它跑起来

1、Controller层

老司机教你用原生JDK 撸一个 MVC 框架!!!

2、Service层

老司机教你用原生JDK 撸一个 MVC 框架!!!
老司机教你用原生JDK 撸一个 MVC 框架!!!

3、Dao层

老司机教你用原生JDK 撸一个 MVC 框架!!!
老司机教你用原生JDK 撸一个 MVC 框架!!!

4、运行结果

老司机教你用原生JDK 撸一个 MVC 框架!!!

到这里,一个迷你版的 Spring MVC 就开发完成了。