SpringMVC--01--简介

初识SpringMVC

Servlet的缺点

1、通常情况下,一个Servlet类只负责处理一个请求,若项目中有成百上千个请求需要处理,就需要有成百上千个Servlet类,这样会使得项目中Servlet类的个数暴增;

2、在Servlet3.0版本之前,每一个Servlet都需要在web.xml文件中至少做八行配置信息,配置内容多且繁琐。当Servlet特别多时,web.xml配置量太多,不利于团队开发;

3、当通过客户端提交参数到服务器,通过Servlet进行接收时,无论数据本身是什么格式,在Servlet中一律按照字符串进行接收,后期需要进行类型转换,复杂类型还需要特殊处理,特别麻烦!

String value = request.getParameter(String name);

4、servlet具有容器依赖性,必须放在服务器中运行,不利于单元测试;

SpringMVC简介

Springmvc是spring框架的一个模块,spring和springmvc无需中间整合层整合

Springmvc是一个基于mvc的web框架

在这里插入图片描述

SpringMVC五大组件

  • 前端控制器(DispatcherServlet)
  • 处理器映射器(HandlerMapping)
  • 处理器适配器(HandlerAdapter)
  • 视图解析器(ViewReslover)
  • 视图渲染(View)

SpringMVC执行原理

提示:DispatcherServlet的作用:接收请求,调用其它组件处理请求,响应结果,相当于转发器、中央处理器,是整个流程控制的中心

  1. 用户发送请求 至 前端控制器(DispatcherServlet);

  2. 前端控制器(DispatcherServlet)收到请求后调用处理器映射器(HandlerMapping),处理器映射器(HandlerMapping)找到具体的Controller(可以根据xml配置、注解进行查找),并将Controller返回给DispatcherServlet;

  3. 前端控制器(DispatcherServlet)调用处理器适配器(HandlerAdapter)。处理器适配器经过适配调用具体的Controller;(Controller–> service --> Dao --> 数据库)
    Controller执行完成后返回ModelAndView,处理器适配器(HandlerAdapter)将controller执行的结果(ModelAndView)返回给前端控制器(DispatcherServlet);

提示:Model(模型数据,即Controller处理的结果,Map) View(逻辑视图名,即负责展示结果的JSP页面的名字)

  1. .前端控制器(DispatcherServlet)将执行的结果(ModelAndView)传给视图解析器(ViewReslover)
    视图解析器(ViewReslover)根据View(逻辑视图名)解析后返回具体JSP页面

  2. 前端控制器(DispatcherServlet)根据Model对View进行渲染(即将模型数据填充至视图中);(默认会存到request域中)
    前端控制器(DispatcherServlet)将填充了数据的网页响应给用户。

其中整个过程中需要开发人员编写的部分有ControllerServiceDaoView;

SpringMVC执行详解

  1. 在SpringMVC框架启动之初,程序会对
    处理器映射器(HandlerMapping)的进行实例化,其中处理器映射器(HandlerMapping)中会有一个map的结构类型.其中map中的key存储的是你要拦截请求路径,value存储的是
    你要具体要执行的请求方法. 所以在SpringMVC框架启动之初,
    处理器映射器(HandlerMapping)会把所有请求的注解,和他标识的相关方法进行统一的记录.
  2. 如果有用户发来请求,首先会被前端控制器(DispatcherServlet所拦截,前端控制器(DispatcherServlet)收到请求后调用处理器映射器(HandlerMapping),通过相关路径匹配,找到具体的Controller(可以根据xml配),并将Controller返回给DispatcherServlet;
  3. 前端控制器(DispatcherServlet)调用处理器适配器(HandlerAdapter)。处理器适配器根据你标识的注解,调用相对应的handler处理器,由这个handler处理器来做具体的调用.Controller;(Controller–>service --> Dao --> 数据库) 最后将controller执行的结果(ModelAndView)对象返回给前端控制器(DispatcherServlet);
  4. 前端控制器(DispatcherServlet)将执行的结果(ModelAndView)传给视图解析器(ViewReslover)
    视图解析器(ViewReslover)根据View(逻辑视图名)解析后返回具体JSP页面
  5. 前端控制器(DispatcherServlet)根据Model对View进行渲染(即将模型数据填充至视图中); 前端控制器(DispatcherServlet)将填充了数据的网页响应给用户。

SpringMVC流程

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

SpringMVC拦截器

工作原理

Spring MVC中的拦截器基于回调机制,可以在目标方法执行之前,先进行业务检测,满足条件则放行,不满足条件则进行拦截,拦截器原理分析如下图所示:

在这里插入图片描述
SpringMVC拦截器工作原理
在这里插入图片描述
HandlerInterceptor在这里插入图片描述

案例

HandlerInterceptor 拦截器

@Component  //spring容器管理对象
public class UserInterceptor implements HandlerInterceptor {

    @Autowired
    private JedisCluster jedisCluster;

    //Spring版本升级 4 必须实现所有的方法  spring 5 只需要重写指定的方法即可.

    /**
     * 需求:   拦截/cart开头的所有的请求进行拦截.,并且校验用户是否登录.....
     * 拦截器选择: preHandler
     * 如何判断用户是否登录:  1.检查cookie信息   2.检查Redis中是否有记录.
     *          true : 请求应该放行
     *          false: 请求应该拦截 则配合重定向的语法实现页面跳转到登录页面 使得程序流转起来

     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        //1.判断用户是否登录  检查cookie是否有值
        String ticket = CookieUtil.getCookieValue(request,"JT_TICKET");
        //2.校验ticket
        if(!StringUtils.isEmpty(ticket)){
            //3.判断redis中是否有值.
            if(jedisCluster.exists(ticket)){
                //4.动态获取json信息
                String userJSON = jedisCluster.get(ticket);
                User user = ObjectMapperUtil.toObj(userJSON,User.class);
                request.setAttribute("JT_USER",user);
                return true;
            }
        }
        response.sendRedirect("/user/login.html");
        return false;
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        //销毁数据
        request.removeAttribute("JT_USER");
    }
}

WebMvcConfigurer— springmvc 配置类

@Configuration
public class MvcConfigurer implements WebMvcConfigurer{
	


	//添加拦截器
	@Autowired
	private UserInterceptor userInterceptor;

	@Override
	public void addInterceptors(InterceptorRegistry registry) {

		registry.addInterceptor(userInterceptor).addPathPatterns("/cart/**","/order/**");

	}

}

各种拦截器Filer

在这里插入图片描述

SpringMVC基于Servlet进行封装的框架

在这里插入图片描述

关于SpringMVC参数提交问题说明

1 简单参数传参问题

1.页面url标识

2.Controller中的方法

 @RequestMapping("/xxx")
public void xxx(String name,int age){
}

2 使用对象方法接收参数

1.页面url标识

2.Controller中的方法

@RequestMapping("/xxx")
public void xxx(User user){
}

public class User{     //pojo类
	private Integer name;
	private String age;
}

3 使用对象的引用为参数赋值

难点: 属性的重名提交问题…
解决思路: 可以采用对象引用的方式为属性赋值.

<input  name="name"   value="二郎神"	/>
<input  name="age"   value="3000"	/>
<input  name="dog.name"   value="哮天犬"	/>
<input  name="dog.age"   value="8000"	/>

Controller中的方法

@RequestMapping("/xxx")
public void  xxx(User user){
	
	}
	
	public class Dog{
		private String name;
		private Integer age;	
	}
	public class User{
		private String name;
		private Integer age;	
		private Dog dog;
	}

不同注解的含义

  • @RequestMapping(“/xxx”) 页面url路径
  • @GetMapping(“/xxx”) 页面get请求 才会拦截
  • @PostMapping(“/xxx”) 页面post请求 才会拦截

Spring MVC 接收参数的几个注解

在这里插入图片描述

  • @RequestParam 键值对参数,只要前端参数name属性,和后端接收名字的一致,新版本Springboot项目中.注解可省略.

  • @PathVariable 请求路径参数 ,运用restfun风格{module} 注解不可省略
    在这里插入图片描述

  • @RequestBody 完整接收post请求协议的内容,转成pojo集合
    在这里插入图片描述

springmvc响应数据

Model的使用

当请求发起访问Controller中的方法时,可以通过参数声明,在方法内使用Model。

@RequestMapping("/doorList")
public String doorList(Model model){

}

Model对象实际上是一个Map集合,例如:往model中添加一个属性

model.addAttribute(String name, Object value);

其中,addAttribute方法会将属性保存到request域中,再通过转发将属性数据带到相应的JSP中,通过${}取出并显示。

案例,往Model中添加属性

@RequestMapping("/testModel")
public String testModel(Model model){
	/* 往Model添加属性 */
	model.addAttribute("name", "小雨");
	model.addAttribute("age", 20);
	return "home";
}
<body>
	<h1>hello springmvc~~~</h1>
	${ name } <br/>
	${ age }
</body>

实际代码

controller

@RequestMapping("/{itemid}")
    public String findItemById(@PathVariable Long itemid, Model model){

        Item item= dubboItemService.findItemById( itemid);
        ItemDesc itemDesc= dubboItemService.findItemDescById(itemid);

        model.addAttribute("item", item);
        model.addAttribute("itemDesc",itemDesc);
        return "item";

    }

item.jsp
在这里插入图片描述

转发(forward)和重定向(redirect)

实现转发(forward)

在request对象的学习中,通过request对象可以实现请求转发(即资源的跳转)。同样的,springmvc也提供了请求转发的方式,具体实现如下:

@RequestMapping("testForward")
public String testForward(){
	System.out.println("测试请求转发(forward)...");
	return "forward:hello";
}

在这里插入图片描述

  • 转发是一次请求,一次响应;
  • 转发后地址栏地址没有发生变化(还是访问testForward的地址);
  • 转发前后的request和response对象也是同一个。

实现重定向(redirect)

在response对象的学习中,通过response对象可以实现请求重定向(即资源的跳转)。

同样的,springmvc也提供了请求重定向的方式,具体实现如下:

@RequestMapping("testRedirect")
public String testRedirect(){
	System.out.println("测试请求重定向(redirect)...");
	return "redirect:hello";
}

在这里插入图片描述

  • 重定向是两次请求,两次响应;
  • 重定向后地址栏地址发生了变化(变为转发后的地址);
  • 并且在重定向前后,request和response对象不是同一个。

RestFul结构

RESTful–介绍

1 请求说明

  • Get请求 http://localhost:8080/user/restFul?id=1&name=张三
  • RestFul请求: http://localhost:8080/user/restFul/1/张三

2 RestFul语法

  1. URL中请求的参数使用/分割
    用户写的: http://localhost:8080/user/restFul/1/张三

  2. 服务器端参数接收时,变量使用{xx}进行包裹,并且位置固定.

  3. 利用@PathVariable注解,动态获取路径中的数据,要求名称必须匹配

 /**
     * RestFul结构 动态接收参数
     * url: http://localhost:8080/user/restFul/1/张三
     * 返回值: 返回User对象
     * 难点: 需要从URL的路径中获取参数!!!
     * 语法:
     *  1.服务器端参数接收时,变量使用{xx}进行包裹,并且位置固定.
     *  2.利用@PathVariable注解,动态获取路径中的数据,要求名称必须匹配
     */
    @RequestMapping("/restFul/{id}/{name}")
    public User restFul(@PathVariable Integer id,
                        @PathVariable String name){
        User user = new User();
        user.setId(id);
        user.setName(name);
        return user;
    }

在这里插入图片描述

3 RestFul结构对象传参

  /**
     * URL: http://localhost:8080/user/restFul2/1/王五/18
     * RestFul对象接收:
     *   如果对象的属性与{key}相同,则可以使用对象接收.
     * 用途: restFul结构 一般用于更新操作
     * @param user
     * @return
     */
    @RequestMapping("/restFul2/{id}/{name}/{age}")
    public User restFul2(User user){

        return user;
    }

4 请求类型与业务的关系

在这里插入图片描述
规则: 随着业务深入,请求类型与业务渐渐的绑定.

  • 新增: post请求类型 @PostMapping(“”)
  • 删除: delete请求类型 @DeleteMapping(“”)
  • 修改: put请求类型 @PutMapping(“”)
  • 查询: get请求类型 @GetMapping(“”)
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值