手写SpringMVC框架

源码地址

1.创建web项目,使用Maven管理项目

      

2.导入servlet-api jar包

    <dependencies>
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>3.0-alpha-1</version>
            <scope>provided</scope>
        </dependency>

        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-lang3</artifactId>
            <version>3.6</version>
        </dependency>

        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>
    </dependencies>

3.创建SpringMVC使用的一些常用的注解类

注解功能说明
RogerResource

使用方法,只能使用在类的成员变量上

根据名称或者成员变量的名称依赖注入实例到对象中去

RogerController

使用方法,只能使用在类上

标记此类是个控制层

RogerService

使用方法,只能使用在类上

标记此类是个服务层,即业务层

RogerRequestMapping

使用方法,既能作用在类上,也能作用在方法上

值是url映射路径

RogerRequestParam

使用方法,只能作用在方法的参数上

值是从前台web浏览器传递过来的参数值

 

4.创建一些使用这些注解的服务类和控制层的类

5.创建SpringMVC核心类RogerDispatcherSevlet

//1 加载属性文件

//2 根据包名扫描项目中所有的class文件
//  这里通过properties文件获取

        // 2.1 获取项目编译后的统一资源定位符

        // 2.2 根据统一资源定位符,获取当前目录文件

        // 2.3 获取当前目录下的所有文件信息

        // 2.4 遍历当前目录文件下的文件信息
        //      如果文件类型是目录,则递归调用扫描包的方法
        //      如果文件类型是文件,则添加到文件存储容器中去

//3 根据(1)获取到的class文件全路径,
// 实例化具有注解配置的class,并放入IOC容器

//4 依赖注入
// 把实例化的对象注入到相应的实例化对象中的成员变量

//5 初始化url和method映射关系
//6 实际进行调用controller的方法
        //6.1 获取实际请求的url
 
        //6.2 获取url映射的方法

        //6.3 获取方法的控制类,即方法是不能单独存在的,方法是属于某个类的

        //6.4 获取执行方法所需的参数
        //6.4.1获取参数列表类型
       
        //6.5 反射调用方法
       

6.配置web.xml文件,应用启动的时候加载核心Servlet

<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
  <display-name>SpringMVC by MySelf</display-name>

  <servlet>
    <servlet-name>RogerDispatcherServlet</servlet-name>
    <servlet-class>com.roger.servlet.RogerDispatcherServlet</servlet-class>
    <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>application.properties</param-value>
    </init-param>
    <load-on-startup>0</load-on-startup>
  </servlet>
  
  <servlet-mapping>
    <servlet-name>RogerDispatcherServlet</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>
  
</web-app>
<load-on-startup>作用以及说明
 1.是否在web应用程序启动的时候,加载这个Servlet,即实例化并调用其init()方法
 2.值必须是一个整数,表示servlet加载的顺序
 3.当值为负数或者没有设置,则容器会当servlet被请求时再加载
 4.如果为正数,或者0时,表示容器启动的时候就加载并初始化这个servlet,值越小,优先级越高

 

 

 

 

 

 

说明:参数解析有两种实现方式

1.简单的方式

Class<?>[] argTypes = method.getParameterTypes();
        Object[] args = new Object[argTypes.length];
        int i = 0;
        for(Class argType : argTypes){
            String argClassName = argType.getSimpleName();
            if(ServletRequest.class.isAssignableFrom(argType)){
                args[i++] = req;
            }else if(ServletResponse.class.isAssignableFrom(argType)){
                args[i++] = resp;
            }else{
                Annotation[] paramAnnotations = method.getParameterAnnotations()[i];
                if(paramAnnotations.length <= 0) {
                    continue;
                }
                for(Annotation paramAnnotation : paramAnnotations){
                    if(RogerRequestParam.class.isAssignableFrom(paramAnnotation.getClass())) {
                        RogerRequestParam rogerRequestParam = (RogerRequestParam) paramAnnotation;
                        args[i++] = req.getParameter(rogerRequestParam.value());
                    }
                }
            }
        }

2.使用策略模式实现(见源码)

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值