您现在的位置是:首页 > 编程 > 

springMVC基础

2025-07-27 15:18:52
springMVC基础 一、HelloWorld程序controller代码语言:javascript代码运行次数:0运行复制@Controller public class HelloController { @RequestMapping("/") public String index(){ return "index"

springMVC基础

一、HelloWorld程序

controller

代码语言:javascript代码运行次数:0运行复制
@Controller
public class HelloController {
    @RequestMapping("/")
    public String index(){
        return "index";
    }
    @RequestMapping("/target")
    public String target(){
        return "target";
    }
}

web.xml

代码语言:javascript代码运行次数:0运行复制
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns=";
         xmlns:xsi=";
         xsi:schemaLocation=" .xsd"
         version="4.0">

    <!--
    默认方法
    springmvc的配置文件位于WEB-IF下,默认名称为<servlet-name>-servlet.xml
    例如,以下配置对应配置文件位于WEB-IF下,文件名为springMVC-servlet.xml
    -->
    <!--配置springmvc前端控制器,对浏览器发送的请求统一进行处理-->
<!--    <servlet>
        <servlet-name>springMVC</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>springMVC</servlet-name>
        &lt;!&ndash;
        /  表示拦截所有请求,除了.jsp(jsp属于servlet程序,有专门解析器处理)
        /* 表示所有请求,包括.jsp
        &ndash;&gt;
        <url-pattern>/</url-pattern>
    </servlet-mapping>-->


    <!--配置springmvc前端控制器,对浏览器发送的请求统一进行处理-->
    <servlet>
        <servlet-name>springMVC</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <!--配置spingmvc.xml配置文件的位置和名称-->
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>classpath:springmvc.xml</param-value>
        </init-param>
        <!--将前端控制器初始化提前到服务器启动时-->
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>springMVC</servlet-name>
        <!--
        /  表示拦截所有请求,除了.jsp(jsp属于servlet程序,有专门解析器处理)
        /* 表示所有请求,包括.jsp
        -->
        <url-pattern>/</url-pattern>
    </servlet-mapping>
</web-app>

spring.xml

代码语言:javascript代码运行次数:0运行复制
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns=";
       xmlns:xsi=";
       xmlns:context=";
       xsi:schemaLocation=" .xsd
                            .xsd">
    <!--注解扫描包-->
    <context:component-scan base-package="com.xc"/>
    <!--thymeleaf视图解析器-->
    <!-- 模板解析器 -->
    <bean id="templateResolver" class="SpringResourceTemplateResolver">
        <!-- 模板文件的路径前缀 -->
        <property name="prefix" value="/WEB-IF/templates/" />
        <!-- 模板文件的路径后缀 -->
        <property name="suffix" value=".html" />
        <property name="templateMode" value="HTML" />
        <!-- 配置是否缓存 -->
        <property name="cacheable" value="false" />
        <!-- 默认编码格式 -->
        <property name="characterEncoding" value="UTF-8"/>
    </bean>
    <!-- 模板引擎 -->
    <bean id="templateEngine" class="spring5.SpringTemplateEngine">
        <property name="templateResolver" ref="templateResolver" />
        <property name="enableSpringELCompiler" value="true" />
    </bean>
    <!-- 视图解析器 -->
    <bean class="spring5.view.ThymeleafViewResolver">
        <property name="templateEngine" ref="templateEngine" />
        <property name="characterEncoding" value="UTF-8"/>
    </bean>
</beans>
代码语言:javascript代码运行次数:0运行复制
<!DOCTYPE html>
<html lang="en" xml:th="; xmlns:th=";>
<head>
    <meta charset="UTF-8">
    <title>首页</title>
</head>
<body>
<h1>首页</h1>
<a th:href="@{/target}">访问目标页面target.html</a>
</body>
</html>

http://localhost:8080/springmvc/

总结

  • 浏览器发送请求,前端控制器dispatcherServlet拦截请求
  • 通过springmvc配置文件的扫描组件@Controller到控制器
  • 与@RequestMapping注解value值匹配,处理相应业务方法
  • 返回一个字符串类型的视图名称,该视图名称会被视图解析器解析,加上前缀和后缀组成视图的路径
  • 最后对视图进行渲染,转发到视图对应的页面
二、RequestMapping属性

1) 基本属性

  • value属性(必须设置)是一个字符串类型的数组,表示该请求映射能够匹配多个请求地址所对应的请求
  • method属性是一个RequestMethod类型的数组,表示该请求映射能够匹配多种请求方式的请求
  • params属性是一个字符串类型的数组
    • “param”:要求请求映射所匹配的请求必须携带param请求参数
    • “!param”:要求请求映射所匹配的请求必须不能携带param请求参数
    • “param=value”:要求请求映射所匹配的请求必须携带param请求参数且param=value
    • “param!=value”:要求请求映射所匹配的请求必须携带param请求参数但是param!=value
代码语言:javascript代码运行次数:0运行复制
@Controller
@RequestMapping("/hello")
public class RequestMappingController {
    @RequestMapping(
            value = {"/test1","test2"},
            method = {RequestMethod.GET,RequestMethod.POST},
            params = {"username","password!=12456"}
    )
    public String success(){
        return "success";
    }
}
  1. 对于处理指定请求方法控制器方法,SpringMVC提供了@RequestMapping的派生注解 处理get请求映射 --> @GetMapping 处理post请求映射 --> @PostMapping 处理put请求映射 --> @PutMapping 处理delete请求映射 --> @DeleteMapping
  2. 常用的请求方式get,post,put,delet 目前浏览器只支持get和post,若form表单提交时,为method设置其他请求方法的字符串(put或delete),按照默认get方法处理 若要发送put和delete请求,需要通过spring提供的过滤器HiddenHttpMethodFilter,restfu风格。

2) springMVC支持ant风格路径

  • ?:表示任意的单个字符
  • *:表示任意的0个或多个字符
  • **:表示任意的一层或多层目录

注意:在使用**时,只能使用/**/xxx的方式

) springMVC支持路径占位符(@PathVariable)

代码语言:javascript代码运行次数:0运行复制
<a th:href="@{/hello/restFul/admin/12456}">restful风格路径访问</a><br>
代码语言:javascript代码运行次数:0运行复制
@Controller
@RequestMapping("/hello")
public class RequestMappingController {
    @RequestMapping("/restFul/{username}/{password}")
    public String restFul(@PathVariable("username") String username,@PathVariable("password") String password){
        println("username: "+username+", password: "+password);
        return "success";
    }
}
三、springMVC获取请求参数

1)@RequestParam

代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/testParam")
public String testParam(@RequestParam(value = "user_name",required = false,defaultValue = "admin") 
                        String username){
    return "success";
}

2)@RequestHeader

代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/testParam")
public String testParam(@RequestHeader(value = "Host",required = false,defaultValue = "default") 
                        String host){
    return "success";
}

)@CookieValue

代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/testParam")
public String testParam(@CookieValue(value = "JSESSIOID",required = false,defaultValue = "12456") 
                        String JSESSIOID){
    return "success";
}

4)乱码设置

代码语言:javascript代码运行次数:0运行复制
<filter>
    <filter-name>CharacterEncodingFilter</filter-name>
    <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
    <init-param>
        <param-name>encoding</param-name>
        <param-value>UTF-8</param-value>
    </init-param>
    <init-param>
        <param-name>forceRespeEncoding</param-name>
        <param-value>true</param-value>
    </init-param>
</filter>
<filter-mapping>
    <filter-name>CharacterEncodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>
四、域对象共享数据
  1. 使用servletApi向request域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/servletApi")
public String servletApi(HttpServletRequest request){
    request.setAttribute("key","value");
    return "success";
}
  1. 使用modelAndView向request域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/modelAndView")
public ModelAndView modelAndView(){
    ModelAndView mv = new ModelAndView();
    mv.addObject("key","value");
    mv.setViewame("success");
    return mv;
}
  1. 使用Model向request域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/model")
public String model(Model model){
    model.addAttribute("key","value");
    return "success";
}
  1. 使用map向request域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("map")
public String map(Map<String,Object> map){
    map.put("key","value");
    return "success";
}
  1. 使用modelMap向request域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("modelMap")
public String modelMap(ModelMap modelMap){
    modelMap.addAttribute("key","value");
    return "success";
}
  1. Model、ModelMap、Map的关系 三者类型参数其实本质上都是BindingAwareModelMap类型的
  2. 使用HttpSession向session域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("session")
public String session(HttpSession session){
    session.addAttribute("key","value");
    return "success";
}
  1. 使用HttpSession向application域对象共享数据
代码语言:javascript代码运行次数:0运行复制
@RequestMapping("application")
public String application(HttpSession session){
	ServletContext application = session.getServletContext();
    application.addAttribute("key","value");
    return "success";
}
五、springMVC的视图

1) 转发视图

springMVC中默认的转发视图是InternalResourceView 当控制器方法中所设置的视图名称以“forward:”为前缀时,创建InternalResourceView视图,此时的视图名称不会被springmvc配置文件的视图解析器解析,而是通过转发方式实现跳转。

代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/testForward")
public String testForward(){
	return "forward:/testHello";
}

2) 重定向视图

springMVC中默认的重定向视图是RedirectView 当控制器方法中所设置的视图名称以“redirect:”为前缀时,创建RedirectView视图,此时的视图名称不会被springmvc配置文件的视图解析器解析,而是通过重定向方式实现跳转。

代码语言:javascript代码运行次数:0运行复制
@RequestMapping("/testForward")
public String testForward(){
	return "forward:/testHello";
}

) 视图控制器view-controller

当控制器方法中,仅仅用来实现页面跳转,即只需要视图名称时,可以将处理器方法使用view-controller标签进行表示

代码语言:javascript代码运行次数:0运行复制
<!--
	path:设置处理的请求地址
	view-name:设置请求地址所对应的视图名称
-->
<mvc:view-controller path="/testview" view-name="success" />
六、restful

HTTP协议里面,四个表示操作方式的动词:GET、POST、PUT、DELETE。

代码语言:javascript代码运行次数:0运行复制
@Controller
public class RestFulController {

    @RequestMapping(value = "/user",method = RequestMethod.GET)
    public String getAllUser(){
        println("查询所有用户信息");
        return "success";
    }

    @RequestMapping(value = "/user/{id}",method = RequestMethod.GET)
    public String getUserById(@PathVariable String id){
        println("查询用户信息id: "+id);
        return "success";
    }

    @RequestMapping(value = "/user",method = RequestMethod.POST)
    public String insertUser(String username,String password){
        println("新增用户信息 username:"+username+", password: "+password);
        return "success";
    }

    @RequestMapping(value = "/user",method = RequestMethod.PUT)
    public String updateUser(String username,String password){
        println("修改用户信息 username:"+username+", password: "+password);
        return "success";
    }

}
代码语言:javascript代码运行次数:0运行复制
<!DOCTYPE html>
<html lang="en" xml:th="; xmlns:th=";>
<head>
    <meta charset="UTF-8">
    <title>首页</title>
</head>
<body>
<h1>首页</h1>
<a th:href="@{/target}">访问目标页面target.html</a><br>
<a th:href="@{/user}">查询所有用户信息</a><br>
<a th:href="@{/user/12}">查询单个用户信息</a><br>
<form th:action = "@{/user}" method="post">
    用户名:<input type="text" name="username"><br>
    密  码:<input type="password" name="password"><br>
    <input type="submit" value="添加">
</form>
<form th:action = "@{/user}" method="post">
    <input type="hidden" name="_method" value="put">
    用户名:<input type="text" name="username"><br>
    密  码:<input type="password" name="password"><br>
    <input type="submit" value="修改">
</form>
</body>
</html>

put和delete请求需要配置过滤器

代码语言:javascript代码运行次数:0运行复制
<filter>
    <filter-name>HiddenHttpMethodFilter</filter-name>
    <filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>HiddenHttpMethodFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

过滤器源码

代码语言:javascript代码运行次数:0运行复制
protected void doFilterInternal(HttpServletRequest request, HttpServletRespe respe, FilterChain filterChain) throws ServletException, IOException {
    HttpServletRequest requestToUse = request;
    //必须是post请求
    if ("POST".equals(request.getMethod()) && request.getAttribute("javax.") == null) {
    	//获取key为_method参数
        String paramValue = request.getParameter("_method");
        if (StringUtils.hasLength(paramValue)) {
            String method = (Locale.EGLISH);
            if (ALLOWED_(method)) {
            	//如果包含请求参数_method包含put、delete,则重新包装request
                requestToUse = new HiddenHttpMethodFilter.HttpMethodRequestWrapper(request, method);
            }
        }
    }
    filterChain.doFilter((ServletRequest)requestToUse, respe);
}
代码语言:javascript代码运行次数:0运行复制
//支持put、delete、patch请求
static {
    ALLOWED_METHODS = Collecti.unmodifiableList(Arrays.asList(HttpMethod.(), HttpMethod.(), HttpMethod.()));
    }
代码语言:javascript代码运行次数:0运行复制
private static class HttpMethodRequestWrapper extends HttpServletRequestWrapper {
    private final String method;
    public HttpMethodRequestWrapper(HttpServletRequest request, String method) {
        super(request);
         = method;
    }
    //将getMethod方法重新。以后获取到的方法就是put或delete了
    public String getMethod() {
        return ;
    }
}
七、

1)配置

  • SpringMVC中拦截控制器方法的执行
代码语言:javascript代码运行次数:0运行复制
@Component
public class InterceptorController implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletRespe respe, Object handler) throws Exception {
        println("InterceptorController.preHandle");
        return true;
    }
    @Override
    public void postHandle(HttpServletRequest request, HttpServletRespe respe, Object handler, ModelAndView modelAndView) throws Exception {
        println("InterceptorController.postHandle");
    }
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletRespe respe, Object handler, Exception ex) throws Exception {
        println("InterceptorController.afterCompletion");
    }
}
代码语言:javascript代码运行次数:0运行复制
<mvc:interceptors>
<!--        <bean class="com.xc.InterceptorController" />-->
<!--        <ref bean="interceptorController" />-->
//以上两种配置方式是对dispatcherServlet所处理的请求进行拦截
    <mvc:interceptor>
    	//拦截所有请求
        <mvc:mapping path="/**"/>
        //排除拦截请求
        <mvc:exclude-mapping path="/"/>
        <ref bean="interceptorController" />
    </mvc:interceptor>
</mvc:interceptors>

2)三个抽象方法

  1. preHandle:控制器方法执行前执行preHandle(),其boolean类型的返回值表示是否拦截或放行。
  2. postHandle:控制器方法执行之后执行postHandle()。
  3. afterComplation:处理完视图和模型数据,渲染视图完毕之后执行afterComplation()。

)多个的执行顺序

1、如果每个preHandle都返回true 此时多个执行顺序和在SpringMVC的配置文件的配置顺序有关 preHandle()会按照配置顺序执行,而postHandle()和afterCOnplation()会按照配置的反序执行

2、如果某个的preHandle返回了false preHandle()返回false和它之前的的preHandle()都会执行,postHandle()都不会执行,返回false的和它之前的的afterComplation()会执行

4)源码

代码语言:javascript代码运行次数:0运行复制
//执行控制器方法前执行
if (!mappedHandler.applyPreHandle(processedRequest, respe)) {
    return;
}
//执行控制器方法(Controller方法)
mv = ha.handle(processedRequest, respe, mappedHandler.getHandler());
if (asyncManager.isConcurrentHandlingStarted()) {
    return;
}
//默认视图名
this.applyDefaultViewame(processedRequest, mv);
//执行控制器方法后执行
mappedHandler.applyPostHandle(processedRequest, respe, mv);
//执行结果(封装处理)
this.processDispatchResult(processedRequest, respe, mappedHandler, mv, (Exception)dispatchException);
代码语言:javascript代码运行次数:0运行复制
boolean applyPreHandle(HttpServletRequest request, HttpServletRespe respe) throws Exception {
	//将多个按顺序一一遍历
    for(int i = 0; i < this.interceptorList.size(); this.interceptorIndex = i++) {
        HandlerInterceptor interceptor = (HandlerInterceptor)this.interceptorList.get(i);
        if (!interceptor.preHandle(request, respe, this.handler)) {
            (request, respe, (Exception)null);
            return false;
        }
    }
    return true;
}
代码语言:javascript代码运行次数:0运行复制
void applyPostHandle(HttpServletRequest request, HttpServletRespe respe, @ullable ModelAndView mv) throws Exception {
	//i-- 将多个倒序一一遍历
    for(int i = this.interceptorList.size() - 1; i >= 0; --i) {
        HandlerInterceptor interceptor = (HandlerInterceptor)this.interceptorList.get(i);
        interceptor.postHandle(request, respe, this.handler, mv);
    }

}
代码语言:javascript代码运行次数:0运行复制
if (mv != null && !mv.wasCleared()) {
	//视图渲染,将modle和view合并成一个整体(页面上添加数据)
    this.render(mv, request, respe);
    if (errorView) {
        (request);
    }
} else if (this.logger.isTraceEnabled()) {
    this.("o view rendering, null ModelAndView returned.");
}

if (!WebAsyncUtils.getAsyncManager(request).isConcurrentHandlingStarted()) {
    if (mappedHandler != null) {
    	//视图渲染后执行
        (request, respe, (Exception)null);
    }

}
八、异常处理器

1)基于配置的异常处理

代码语言:javascript代码运行次数:0运行复制
<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver" >
    <property name="exceptionMappings" >
        <props>
            <!--
            properties的键表示处理器方法执行过程中出现的异常
            properties的值表示出现指定异常时候,跳转的视图名称
            -->
            <prop key="java.lang.ArithmeticException">error</prop>
        </props>
    </property>
    <!--exceptionAttribute属性设置一个属性名,将出现的异常信息在请求域中进行共享-->
    <property name="exceptionAttribute" value="ex" />
</bean>

1)基于注解的异常处理

代码语言:javascript代码运行次数:0运行复制
//将当前类标识为异常处理的组件
@ControllerAdvice
public class ExceptionController {
    //用于设置所标识方法处理的异常
    @ExceptionHandler()
    public String handleArithmeticException(Exception ex, Model model){
        model.addAttribute("ex",ex);
        return "error";
    }
}
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。 原始发表:202-10-1,如有侵权请联系 cloudcommunity@tencent 删除基础配置数据string对象

#感谢您对电脑配置推荐网 - 最新i3 i5 i7组装电脑配置单推荐报价格的认可,转载请说明来源于"电脑配置推荐网 - 最新i3 i5 i7组装电脑配置单推荐报价格

本文地址:http://www.dnpztj.cn/biancheng/1162925.html

相关标签:无
上传时间: 2025-07-20 20:43:26

上一篇:SpringMVC源码解析

下一篇:bean的生命周期

留言与评论(共有 18 条评论)
本站网友 windows95
10分钟前 发表
defaultValue = "default") String host){ return "success"; })@CookieValue代码语言:javascript代码运行次数:0运行复制@RequestMapping("/testParam") public String testParam(@CookieValue(value = "JSESSIOID"
本站网友 墨脱隧道
8分钟前 发表
1)配置SpringMVC中拦截控制器方法的执行代码语言:javascript代码运行次数:0运行复制@Component public class InterceptorController implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest request
本站网友 切糕成本
16分钟前 发表
渲染视图完毕之后执行afterComplation()
本站网友 生发黑豆汤
12分钟前 发表
th="; xmlns
本站网友 安诺优达
25分钟前 发表
HttpMethod.())); }代码语言:javascript代码运行次数:0运行复制private static class HttpMethodRequestWrapper extends HttpServletRequestWrapper { private final String method; public HttpMethodRequestWrapper(HttpServletRequest request
本站网友 梦见双胞胎男孩
1分钟前 发表
method = RequestMethod.POST) public String insertUser(String username
本站网友 房产他项权证
14分钟前 发表
可以将处理器方法使用view-controller标签进行表示代码语言:javascript代码运行次数:0运行复制<!-- path:设置处理的请求地址 view-name:设置请求地址所对应的视图名称 --> <mvc
本站网友 形象设计学校
23分钟前 发表
需要通过spring提供的过滤器HiddenHttpMethodFilter
本站网友 老年斑的治疗方法
24分钟前 发表
Object handler
本站网友 沧州房屋出租
30分钟前 发表
渲染视图完毕之后执行afterComplation()
本站网友 海底捞火锅团购
28分钟前 发表
只能使用/**/xxx的方式) springMVC支持路径占位符(@PathVariable)代码语言:javascript代码运行次数:0运行复制<a th
本站网友 物业公司经营范围
1分钟前 发表
ModelMap
本站网友 商银通
22分钟前 发表
respe)) { return; } //执行控制器方法(Controller方法) mv = ha.handle(processedRequest
本站网友 火车票订票软件
2分钟前 发表
delete
本站网友 hui
6分钟前 发表
”为前缀时
本站网友 人保汽车保险
11分钟前 发表
th="; xmlns
本站网友 福田区
22分钟前 发表
即只需要视图名称时