当前位置: 代码网 > it编程>编程语言>Java > Spring MVC核心组件与请求处理流程分析

Spring MVC核心组件与请求处理流程分析

2025年01月17日 Java 我要评论
spring mvc请求处理完整流程详解一、流程文字描述当一个http请求到达服务器后,会经历以下流程:filter链处理(入口)请求首先经过filter链每个filter按照定义的顺序执行dofil

spring mvc请求处理完整流程详解

一、流程文字描述

当一个http请求到达服务器后,会经历以下流程:

filter链处理(入口)

  • 请求首先经过filter链
  • 每个filter按照定义的顺序执行dofilter方法的前置处理
  • filter通过调用chain.dofilter()将请求传递给下一个filter

dispatcherservlet接收请求

  • 所有filter处理完后,请求到达dispatcherservlet
  • dispatcherservlet作为前端控制器,统一处理所有请求

寻找handler

  • dispatcherservlet调用gethandler方法
  • 遍历所有handlermapping,找到与当前url匹配的handler
  • 找到handler后,把handler和对应的拦截器封装成handlerexecutionchain对象

获取handleradapter

  • 根据handler的类型,遍历所有handleradapter
  • 找到支持该handler类型的handleradapter
  • handleradapter用于调用handler并处理参数、返回值等

拦截器前置处理

  • 按顺序调用handlerexecutionchain中所有拦截器的prehandle方法
  • 如果任一拦截器的prehandle返回false,则中断请求处理
  • 中断时会触发已执行的拦截器的aftercompletion方法

handler处理请求

  • 通过handleradapter调用handler(controller方法)
  • handleradapter负责参数解析、类型转换
  • handler执行业务逻辑,返回处理结果

拦截器后置处理

  • handler执行完成后,按逆序调用所有拦截器的posthandle方法
  • 此时视图尚未渲染

视图渲染

  • 根据handler返回的结果进行视图渲染
  • 如果是@restcontroller,将返回值转换为json/xml等格式
  • 如果是传统@controller,解析视图名称并渲染视图

拦截器完成处理

  • 视图渲染完成后,按逆序调用所有拦截器的aftercompletion方法
  • 无论过程中是否有异常,都会执行aftercompletion

filter链处理(出口)

  • 响应会按照与处理请求相反的顺序经过filter链
  • 每个filter执行dofilter方法的后置处理
  • 最终响应返回给客户端

二、关键组件详解

2.1 handlermapping

// 核心数据结构
public class requestmappinghandlermapping {
    // 保存url与处理器方法的映射关系
    private final map<requestmappinginfo, handlermethod> mappinglookup;
}
// 映射示例
mappinglookup = {
    requestmappinginfo{
        patterns=/users/{id},    // url模式
        methods=get,             // http方法
        params=[],              // 请求参数
        headers=[]              // 请求头
    } -> handlermethod{usercontroller.getuser()}
}

2.2 handlerexecutionchain

public class handlerexecutionchain {
    // handler本身(如controller的方法)
    private final object handler;
    // 与handler关联的拦截器列表
    private list<handlerinterceptor> interceptors;
}

2.3 handleradapter

// 处理@requestmapping注解的方法
public class requestmappinghandleradapter implements handleradapter {
    public modelandview handle(request, response, handler) {
        // 1. 解析请求参数
        object[] args = resolveparameters(request, handler);
        // 2. 调用controller方法
        object returnvalue = invokemethod(handler, args);
        // 3. 处理返回值
        return processreturnvalue(returnvalue);
    }
}

2.4 视图渲染

// 1. @restcontroller(json渲染)
@getmapping("/api/user")
public user getuser() {
    return user;  // 自动转换为json
}
// 2. @controller(html渲染)
@getmapping("/user")
public string user(model model) {
    model.addattribute("user", user);
    return "userview";  // 解析为具体视图
}

三、拦截器执行流程

3.1 拦截器定义

public class loginterceptor implements handlerinterceptor {
    @override
    public boolean prehandle(request, response, handler) {
        system.out.println("loginterceptor - prehandle");
        return true;
    }
    @override
    public void posthandle(request, response, handler, mv) {
        system.out.println("loginterceptor - posthandle");
    }
    @override
    public void aftercompletion(request, response, handler, ex) {
        system.out.println("loginterceptor - aftercompletion");
    }
}

3.2 执行顺序示例

filter1 - 请求处理
    filter2 - 请求处理
        loginterceptor - prehandle
            securityinterceptor - prehandle
                controller方法执行
            securityinterceptor - posthandle
        loginterceptor - posthandle
        视图渲染
            securityinterceptor - aftercompletion
        loginterceptor - aftercompletion
    filter2 - 响应处理
filter1 - 响应处理

3.3 拦截器调用过程

// 1. prehandle调用(正序)
for (handlerinterceptor interceptor : interceptors) {
    if (!interceptor.prehandle(request, response, handler)) {
        triggeraftercompletion(request, response, handler, null);
        return false;
    }
}
// 2. posthandle调用(逆序)
for (int i = interceptors.length - 1; i >= 0; i--) {
    interceptors[i].posthandle(requestresponse, handler, mv);
}
// 3. aftercompletion调用(逆序)
for (int i = interceptors.length - 1; i >= 0; i--) {
    interceptors[i].aftercompletion(request, response, handler, ex);
}

到此这篇关于spring mvc核心组件与请求处理流程的文章就介绍到这了,更多相关spring mvc请求处理内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com