springMVC(一)—— 入门

  • mybatis的核心设计是<resultMap>

  • spring的核心设计是<bean>(别跟我提IOC和AOP思想)

  • springMVC的核心就是servlet

一、认识SpringMVC

1、 SpringMVC是什么

  SpringMVC 是 Spring 框架内置的 MVC 的实现。SpringMVC 就是一个 Spring 内置的 MVC 子框架

  Spring 子框架:意味着 SpringMVC 的包都在 Spring 框架里面。

  MVC:Model-View-Control(模型--视图--控制器),这是一个解决页面代码(视图代码)和后台代码分离的设计思想。

2、SpringMVC的作用

  MVC 模式(Model-View-Controller):为了解决页面代码和后台代码的分离。

  既然 SpringMVC 是一个 MVC 框架,首先就要解决 MVC 理念提出的问题。页面代码和后台代码分离。

3、为什么要学习 SpringMVC

  问题:我们已经学习了 Servlet/JSP 了。为什么还要学习 SpringMVC 呢?

  我们知道,Servlet /JSP就是一套MVC模式的实现!!SpringMVC也是MVC的实现,那么学SpringMVC的意义在哪里?

  SpringMVC不仅仅是MVC的实现,它还是一个框架。这意味着,除了MVC的实现以外还提供了大量的辅助页面请求处理的功能组件!!!

  ① 支持直接一个方法对一个请求

  ② 支持数据的自动封装

  ③ 自动支持上传组件

  ④ 自动支持JSON的转成

一、回顾servlet

为什么要回顾servlet?因为springMVC的底层是servlet

Servlet 是一种实现动态页面的技术。我们可以继承httpServlet接口写一个自己的servlet类,所以也可以把servelet理解成一个java类

这个servlet类运行起来的作用就是收集前端的request请求,映射到后端业务逻辑,再把后端的结果返回给前端(或者直接理解成分割前端和后端更好一些),实现动态页面。

之前学tomcat的时候没有手动开启过servlet,因为tomcat内置了servlet。

现在我们手动写一个自己的servlet,主要分2步:

  1. 创建一个java类并且继承HttpServlet,重写doGet()或者doPost()方法

  1. 在web.xml里注册servlet

1.1 创建maven项目,导入jar包,提升为web项目

创建一个空的maven project

删掉项目的src目录

在project下创建一个空的maven module(也不选webapp模板),然后将其提升为web项目

就出现了webapps的发布目录:

PS:通过tomcat发布一个项目project01,将其上下文改为“/”(不改的话,访问这个项目的url是localhost:8080/project01),则localhost:8080/默认定位到web目录下,也就是这个项目,如果我在web下新建一个/new/new.jsp,访问的url便是localhost:8080/new/new.jsp 。web下的网页是公开的,为了更安全我们可以放在web/WEB-INF下

导入jar包(最好project的pom.xm文件和module的pom.xml文件都导,这样方便把module拷给别人。而且打包的时候maven会自动查重并不会打两份)

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

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-webmvc</artifactId>
    <version>5.3.16</version>
</dependency>

<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>servlet-api</artifactId>
    <version>2.5</version>
</dependency>

1.2继承HttpServlet类

新建包,新建MyServlet类,继承HttpServlet类

重写doGet和doPost方法

package com.company.kuang;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

public class MyServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //1.获取前端request参数
        String method = req.getParameter("method");
        if(method.equals("add")){
            req.getSession().setAttribute("msg","执行了add方法");
        }
        if(method.equals("delete")){
            req.getSession().setAttribute("msg","执行了delete方法");
        }
        //2.调用后端业务层
            //在这里我们只是测试,所以不写了
        //3.视图转发或重定向
        req.getRequestDispatcher("WEB-INF/jsp/test.jsp").forward(req,resp);
    }

    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req,resp);  //直接调用上面的doGet
    }
}

PS:如果有两个页面,那么就要写两个servlet类,然后在web.xml里注册两个servlet。

首页的配置:

跳转页面的创建:在web/WEB-INF下新建jsp/test.jsp,让其获取msg

<html>
<head>
    <title>Title</title>
</head>
<body>
${msg}    
</body>
</html>

1.3 在web.xml里注册servlet

   <?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <servlet>
        <servlet-name>myservlet</servlet-name>
        <servlet-class>com.company.kuang.MyServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>myservlet</servlet-name>
        <url-pattern>/hello</url-pattern> 
<!--访问localhost:8080/项目站名/hello  就会被servlet拦截
 不过我们一般把项目站名配置为‘/’-->
    </servlet-mapping>

</web-app>

1.4 给项目配置tomcat

由于我们建的是maven项目,不像springboot内置了tomcat,我们需要手动给这个项目配置我们本地的tomcat。

下面是在给tomcat配置项目,不然你有四五个项目,tomcat也不知道该替你跑哪个呀

1.5 测试

二、springMVC原理讲解

2.1 手动实现springMVC

从此以后不用再手动写servlet了!之前访问多个页面要写多个servlet,现在出现了一个servlet的集中调度器DispatcherServlet,只用一个DispatcherServlet,它可以帮我们匹配所有页面。现在我们不需要写多个servlet了,但是需要写多个controller类。

2.1 在web.xml里配置spring帮我们写好的DispatcherServlet

2.2 xml配置

2.3 手动编写Controller

因为在上面的springmvc-servlet.xml中配置了前缀/WEB-INF/jsp和后缀.jsp,所以跳转的视图是/WEB-INF/jsp/hello.jsp

2.2 springMVC底层原理——解析上述过程

PS:红色线部分是需要我们自己写的,黑色线是springMVC底层实现的

  1. DispatcherServlet表示前端控制器,是整个springMVC的控制中心。用户发出请求,DispatcherServlet接收请求并拦截请求

对应的配置

  1. 我们假设请求的url为:http://localhost:8080/SpringMVC/hello

  1. 如上url拆分成3部分

  1. http://localhost:8080 服务器域名

  1. SpringMVC 部署在服务器上的web站点,我们一般直接用‘/’

  1. hello 控制器

  1. 通过分析,如上url表示为:请求位于服务器localhost:8080上的SpringMVC站点的hello控制器

2~5:根据控制器名字“hello”,找到对应的controller。

对应的配置

具体步骤:

2:HandlerMapping为处理映射,由DispatcherServlet调用。

3:HandlerExecution表示具体的Handler,其主要作用是根据url查找控制器,如上url被查找的控制器为:hello

4:HandlerExecution将解析后的信息传递给DispatcherServlet,如解析控制器映射等

5:HandlerAdapter表示处理器配置器,按照特定的规则去执行Handler

6:Handler让具体的Controller执行

7:Controller将具体的执行信息返回给HandlerAdapter,如ModelAndView

8:HandlerAdapter将视图逻辑名或模型传递给DispatcherServlet

9:DispatcherServlet调用视图解析器(ViewResolver)来解析视图逻辑名

10:视图解析器(ViewResolver)将解析的视图逻辑名传给DispatcherServlet

11:DispatcherServlet调用具体的视图

12:最终视图呈现给用户

三、约定大于配置,使用注解开发springMVC

spring还用着配置文件,但是从springMVC开始,全面使用注解开发

1.创建一个新的maven module,提升为web项目,导入依赖(前门步骤有)

给依赖关闭一下过滤,防止我们的配置文件被“约定大于配置”过滤掉

<build>
        <resources>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>false</filtering>
            </resource>

            <resource>
                <directory>src/main/resources</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>false</filtering>
            </resource>
        </resources>
    </build>

给项目打包增加lib目录

然后apply

2.死配置——DispatcherServlet

意思是以后凡是要写springMVC的项目,直接拷进去。

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <!--1.注册DispatcherServlet-->
    <servlet>
        <servlet-name>SpringMVC</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <!--关联SpringMVC配置文件:通过初始化参数指定SpringMVC配置文件的位置-->
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>classpath:springmvc-servlet.xml</param-value>
        </init-param>
        <!--配置DispatcherServlet启动级别:数字越小,启动越早-->
        <load-on-startup>1</load-on-startup>
    </servlet>

    <!--所有请求都会被springmvc拦截-->
    <servlet-mapping>
        <servlet-name>SpringMVC</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>
</web-app>

3.死配置——springmvc配置文件

  1. handler映射器

  1. handler适配器

  1. 视图解析器

意思是以后凡是要写springMVC的项目,直接拷进去。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        https://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        https://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/mvc
        https://www.springframework.org/schema/mvc/spring-mvc.xsd">

    <!--自动扫描扫描指定包里的注解(我们创建一个com.kuang.controller包,用来写controller)-->
    <context:component-scan base-package="com.kuang.controller"></context:component-scan>
    <!--开启注解的支持-->
    <!--<context:annotation-config/>-->
    <!--让springMVC不处理静态资源-->
    <mvc:default-servlet-handler/>

    <!--
     ①替代了之前的handler映射器和handler适配器的配置。
     ②要想使@RequestMapping注解生效,必须向上下文中注册handler映射器和handler适配器的实例
     annotation-driver配置自动帮我们完成了!
    -->
    <mvc:annotation-driven/>

    <!--视图解析器-->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"
        id="internalResourceViewResolver">
        <!--前缀-->
        <property name="prefix" value="/WEB-INF/jsp/" />
        <!--后缀-->
        <property name="suffix" value=".jsp"/>
    </bean>
</beans>

里面的<mvc:annotation-driven>注解就是替代了下面这两行配置。

根据视图解析器的配置,我们知道,要把jsp页面建在/WEB-INF/jsp下

4. 编写Controller

如果返回值是String,并且有具体的页面可以跳转(意思是我们写了hello.jsp),那么就会被视图解析器解析。如果没有写hello.jsp,那么访问的时候会报404错误。

@Controller
public class MyController {

    @RequestMapping("/hello")
    public String hello(Model model){ 
        //封装数据
        model.addAttribute("msg","Hello,SpringMVC!");
        return "hello"; //视图名,会被视图解析器处理(拼接成/WEB-INF/jsp/hello.jsp)
    }
}

PS:方法的参数可以用Model或者ModelAndView,Model是ModelAndView的简化版

5. 编写要跳转的jsp页面

在/WEB-INF目录下新建jsp目录,创建hello.jsp

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>Title</title>
</head>
<body>
${msg}
</body>
</html>

处理过程:用户请求localhost:8080/hello后,会被DispatcherServlet拦截(根据DispatcherServlet的配置,所有localhost:8080/请求都被拦截),然后分发给@RequstMapping("/hello")对应的controller,controller调用业务层,然后封装数据,跳转到hello.jsp显示,

来开启tomcat测试一下,重新配置一下tomcat要发布的新项目

四、controller控制器详解

实现controller的两种方式:① 注解(√) ②实现接口(×)

五、@RequestMapping详解

六、Restful 风格

普通风格:

前端要①用?分割方法和参数 ②指定参数名 ③多个参数用&连接

Restful风格

前端要这样写:①不用写参数名了 ②不同的参数用/分割

七、重定向和转发的区别

7.1 重定向与转发的区别

1.重定向访问服务器两次,转发只访问服务器一次。

2.转发页面的URL不会改变,而重定向地址会改变

3.转发只能转发到自己的web应用内,重定向可以重定义到任意资源路径。

4.转发相当于服务器跳转,相当于方法调用,在执行当前文件的过程中转向执行目标文件,两个文件(当前文件和目标文件)属于同一次请求,前后页 共用一个request,可以通过此来传递一些数据或者session信息,request.setAttribute()和 request.getAttribute()。而重定向会产生一个新的request,不能共享request域信息与请求参数

5.由于转发相当于服务器内部方法调用,所以转发后面的代码仍然会执行(转发之后记得return);重定向代码执行之后是方法执行完成之后进行重定向操作,也就是访问第二个请求,如果是方法的最后一行进行重定向那就会马上进行重定向(重定向也需要return)。

6.无论是RequestDispatcher.forward方法,还是HttpServletResponse.sendRedirect方法,在调用它们之前,都不能有内容已经被实际输出到了客户端。如果缓冲区中已经有了一些内容,这些内容将被从缓冲区中移除。

可以这么理解

  转发相当于,张三向你借钱,但是你兜里没钱,所以你去找李四借到钱之后借给张三。对于张三而言并不知道你的钱是和李四借的。

  重定向相当于,张三向你借钱,你兜里没钱,你告诉他李四有钱,所以张三再次去找李四借钱。

7.2 调用方式

转发和重定向在Java中的方法如下:

request.getRequestDispatcher("/SecondServlet?addParam=newParam").forward(request, response);
response.sendRedirect("/WebSocket/SecondServlet");

  WebSocket相当于项目名称,SecondServlet是具体的servlet请求。也就是转发不加项目名称,重定向可以写绝对URL,也可以写相对URL。

补充:3xx状态码与重定向相关。301是永久重定向,302是临时重定向,我们有时候希望发送永久重定向的code。上面sendRedirect默认是302。如下:

        response.setStatus(301);
        response.addHeader("Location", "/WebSocket/SecondServlet");

7.3 应用场景

1. 转发 request.getRequestDispatcher().forward(request,response):

  • 属于转发,也是服务器跳转,相当于方法调用,在执行当前文件的过程中转向执行目标文件,两个文件(当前文件和目标文件)属于同一次请求,前后页 共用一个request,可以通过此来传递一些数据或者session信息,request.setAttribute()和 request.getAttribute()。

  • 在前后两次执行后,地址栏不变,仍是当前文件的地址。

  • 不能转向到本web应用之外的页面和网站,所以转向的速度要快。

  • URL中所包含的“/”表示应用程序(项目)的路径。

2. 重定向 response.sendRedirect():

  • 属于重定向,也是客户端跳转,相当于客户端向服务端发送请求之后,服务器返回一个响应,客户端接收到响应之后又向服务端发送一次请求,一共是2次请求,前后页不共用一个request,不能读取转向前通过request.setAttribute()设置的属性值。

  • 在前后两次执行后,地址栏发生改变,是目标文件的地址。

  • 可以转向到本web应用之外的页面和网站,所以转向的速度相对要慢。

  • URL种所包含的"/"表示根目录的路径。

  特殊的应用:对数据进行修改、删除、添加操作的时候,应该用response.sendRedirect()。如果是采用了 request.getRequestDispatcher().forward(request,response),那么操作前后的地址栏都不会发生 改变,仍然是修改的控制器,如果此时再对当前页面刷新的话,就会重新发送一次请求对数据进行修改,这也就是有的人在刷新一次页面就增加一条数据的原因。

7.4 springMVC使用重定向和转发

有使用视图解析器和不使用视图解析器两种方式,但是我们99%情况下都使用视图解析器。

有视图解析器的情况下,默认是转发,如果想要重定向,加一个“redirect:”

八、获取前端传来的请求参数及回显给前端

8.1 获取前端传来的请求参数

(1)当url里的参数和controller方法里的参数名称相同时
(2)当url里的参数和controller方法里的参数名称不同时

此时应该用到@RequestParam注解。这个注解和mybatis的@Param注解一样,无论参数名称是否相同,都加上他这个注解,这是编码的规范。

(3)当controller方法里的参数是一个对象时

而且智能的是,如果url中只有部分参数名匹配上了User的成员变量名,那么匹配上的部分就有值,没匹配上的为null。

8.2 回显给前端的3种方式

@RequestMapping("/test")
public void test(Model model){
                //ModelAndView modelAndViw
                //ModelMap modelMap

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值