SpringMVC入门

一、SpringMVC概述

SpringMVC是Spring中的一个组件,SpringMVC用于web层,相当于controller(等价于传统的servlet和struts的action,或者hendler),用来处理用户请求。 同时,SpringMVC也是一种基于Java的实现MVC设计模式的请求驱动类型的轻量级Web框架,使用了MVC架构模式的思想,将web层进行职责解耦。举个例子,用户在地址栏输入http://网站域名/login,那么springmvc就会拦截到这个请求,并且调用controller层中相应的方法,(中间可能包含验证用户名和密码的业务逻辑,以及查询数据库操作,但这些都不是springmvc的职责),最终把结果返回给用户,并且返回相应的页面(当然也可以只返回json/xml等格式数据)。springmvc就是做前面和后面过程的活,与用户打交道!!springmvc需要有spring的jar包作为支撑才能跑起来,所以需要Spring的基础。

总结: SpringMVC作用相当于servlet,但是简化了servlet的复杂操作,将这部分复杂操作交给框架去实现

二、Springmvc处理流程

在这里插入图片描述

在springmvc的各个组件中,处理器映射器、处理器适配器、视图解析器称为springmvc的三大组件

以下组件通常使用框架提供实现:

  • DispatcherServlet:前端控制器
    用户请求到达前端控制器,它就相当于mvc模式中的c,dispatcherServlet是整个流程控制的中心,由它调用其它组件处理用户的请求,dispatcherServlet的存在降低了组件之间的耦合性。
  • HandlerMapping:处理器映射器
    HandlerMapping负责根据用户请求url找到Handler即处理器,springmvc提供了不同的映射器实现不同的映射方式,例如:配置文件方式,实现接口方式,注解方式等。
  • Handler:处理器
    Handler 是继DispatcherServlet前端控制器的后端控制器,在DispatcherServlet的控制下Handler对具体的用户请求进行处理。
    由于Handler涉及到具体的用户业务请求,所以一般情况需要程序员根据业务需求开发Handler。
  • HandlAdapter:处理器适配器
    通过HandlerAdapter对处理器进行执行,这是适配器模式的应用,通过扩展适配器可以对更多类型的处理器进行执行。
  • ViewResolver:视图解析器
    View Resolver负责将处理结果生成View视图,View Resolver首先根据逻辑视图名解析成物理视图名即具体的页面地址,再生成View视图对象,最后对View进行渲染将处理结果通过页面展示给用户。

开发流程:

  1. 导入相应的依赖
  2. 在web.xml中配置SpringMVC的核心控制器
  3. 在web.xml中指定配置文件的路径
  4. 在springmvc的配置文件中,扫描具有注解的类,同时使springmvc的注解生效
  5. 在controller类上添加注解@Controller
  6. 给该类中的方法添加@RequstMapping注解,表示请求地址

三、SpringMVC入门案例(注解版)

第一步:新建项目

在 IDEA 中新建 Spring MVC 项目(IDEA会自动帮我们导入SpringMVC所需要的jar包),并且取名为 【HelloSpringMVC】,点击【Finish】

在这里插入图片描述

在这里插入图片描述

第二步:修改 web.xml

web.xml配置如下:

<?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">

<!-- 配置SpringMVC前端控制器DispatcherServlet(固定写法) -->
<servlet>
    <servlet-name>springDispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    
    <!-- SpringMVC的配置文件所在的位置和名称(默认在src下,如果是maven,则是在resource中) -->
    <init-param>
        <param-name>contextConfigLocation</param-name>
      <!--框架进行转发规则的定义文件-->
        <param-value>classpath:springmvc.xml</param-value>
    </init-param>
	
    <!--表示服务器一启动,最优先加载前端控制器DispatcherServlet-->
    <load-on-startup>1</load-on-startup>
</servlet>

<servlet-mapping>
    <servlet-name>springDispatcherServlet</servlet-name>
    <!-- SpringMVC拦截所有请求,再进行转发 -->
    <url-pattern>/</url-pattern>
</servlet-mapping>

<!-- 配置编码级过滤器,防止中午乱码 -->
    <!-- 编码级过滤器 -->
    <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>
    </filter>

    <filter-mapping>
        <filter-name>characterEncodingFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
</web-app>

<url-pattern>元素的值改为 *.form(或者其他的名字),表示要拦截请求以.form结尾的请求,并交由Spring MVC的后台控制器来处理,改完之后:

<servlet-mapping>
    <servlet-name>dispatcher</servlet-name>
    <url-pattern>*.form</url-pattern>
</servlet-mapping>

说明:

  • 方式一: *.form , 可以访问以.form结尾的地址,由DispatcherServlet进行解析。此方法最简单,不会导致静态资源(jpg,js,css)被拦截。【开发中经常使用】
  • 方式二:/ ,所有访问的地址都由DispatcherServlet进行解析,此方法可以实现REST风格的url,很多互联网类型的应用使用这种方式。但是此方法会导致静态文件(jpg,js,css)被拦截后不能正常显示,所以对静态文件的解析需要配置不让DispatcherServlet进行解析。【开发中建议使用】

第三步:创建springmvc.xml文件

在src目录下创建SpringMVC的配置文件springmvc.xml,并加入如下代码

<?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:mvc="http://www.springframework.org/schema/mvc"
	xmlns:context="http://www.springframework.org/schema/context"
	xmlns:aop="http://www.springframework.org/schema/aop" 
	xmlns:tx="http://www.springframework.org/schema/tx"
	xsi:schemaLocation="http://www.springframework.org/schema/beans 
		http://www.springframework.org/schema/beans/spring-beans.xsd 
		http://www.springframework.org/schema/mvc
		http://www.springframework.org/schema/mvc/spring-mvc.xsd
		http://www.springframework.org/schema/context 
		http://www.springframework.org/schema/context/spring-context.xsd 
		http://www.springframework.org/schema/aop 
		http://www.springframework.org/schema/aop/spring-aop.xsd 
		http://www.springframework.org/schema/tx 
		http://www.springframework.org/schema/tx/spring-tx.xsd">

<!-- 配置扫描包,告诉SpringMVC被注解的class都在哪个包下 -->
<context:component-scan base-package="com.myw.controller"></context:component-scan>
<aop:aspectj-autoproxy proxy-target-class="true"></aop:aspectj-autoproxy>
<!-- 使springmvc的注解生效 -->
<mvc:annotation-driven ></mvc:annotation-driven>

<!--静态资源过滤器  -->
	springmvc默认不支持静态资源(html/css/js/img..),所以需要配置静态资源过滤器
	<!--
	location:"/"要过滤静态资源路径
	mapping="/**"表示要过滤哪些内容
	  -->
	<mvc:resources location="/" mapping="/**"></mvc:resources>

<!--
	//配置处理器映射器
	<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping" />

	//配置处理器映射器 
	<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping" />
-->

<!--
	直接配置处理器映射器和处理器适配器比较麻烦,可以使用注解驱动annotation-driven来加载
-->

<!--
//配置视图解析器,告诉SpringMVC在网站的哪个目录下能找到jsp文件(现在一般不用jsp,所以这一段一般可以不写) 
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <property name="prefix" value="/WEB-INF/views/"></property>
    <property name="suffix" value=".jsp"></property>
</bean>
-->
</beans>

第四步:编写接受请求的控制器

相当于编写servlet

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
public class HelloWorld {
    /**
     * 1. 使用RequestMapping注解来映射请求的URL,写在方法上面,一个请求对应一个方法
     * 2. 使用ResponseBody注解(Ajax常用此法返回值,如果是其他对象,则返回json对象)
     * 当返回值是String,并且方法上方有此注解时,返回的字符串将不在被解析为springmvc的视图(即jsp文件),会被
     * 直接以字符串展示在浏览器里
     */
    @RequestMapping("helloworld")
    @ResponseBody
    public String hello(){
        System.out.println("hello world");
        return "success";
     }
}

注:

@Controller 注解:
很明显,这个注解是用来声明控制器的,但实际上这个注解对 Spring MVC 本身的影响并不大。

@RequestMapping 注解:
很显然,这就表示路径 helloworld 会映射到该方法上

第五步:开启tomcat

在这里插入图片描述

在这里插入图片描述

修改端口号为http的默认端口80(非必须),并且找到安装好的tomcat(Application server)

在这里插入图片描述

修改项目的虚拟路径名

在这里插入图片描述

第六步:准备前端html页面,通过ajax跳转请求并获取相应的返回结果

$.ajax({
                url:"helloworld",
                type:"post",
                //data:{"username":username,"password":password},
                //dataType:"json",
                success:function (result){
                    console.log(result);
                }
  });

四、 SpringMVC映射规则

二级映射

在类上和方法上同时注解@RequestMapping,相当于地址栏里有两级的地址

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
@RequestMapping("one")
public class TestController {
    @RequestMapping("two")
    public String test(){
        return "index";
    }
}

//如上注解后,映射地址为:http://localhost:8080/xx/one/two

参数绑定的含义

所谓的参数绑定,就是怎么样获取到前台页面传过来的值,通常是跟据参数名(key)来获取值;

//页面端提交请求的程序
$.post("../hc.v",
    {
        name : "shoji",
        price : "8888"
    },
    function(d) {
        alert(d);
    }
)
//后台响应上面ajax的post请求的代码
//通过两段代码里“name”和“price”的相同,把“shouji”和“8888”传到hc方法里
//问号传值的方式同样适用    ?name=shoji&price=88882.
...
//这里一般会添加@Responsebody或者在类上添加    
@RequestMapping("hc.v")
@Responsebody
public String hc(String name,String price){
    return "test";
}
...

映射方法的返回值类型

@ResponseBody注解

  • 当返回值是String,并且方法上方有此注解时,返回的字符串将不在被解析为springmvc的视图(即jsp文件),会被直接以字符串展示在浏览器里(如果是map集合或者pojo类这些有键值对的对象时,则转化为json字符串返回
@RequestMapping("/test")
@ResponseBody
public String hhh() {
    return "first";
}
//first将被ajax接收

注:

这个注解如果这个类中,全是返回ajax请求的方法,则直接在类上写@ResponseBody即可,和@Controller可以合并缩写为@RestController

@RestController
public class HelloSpringMVC{
    
    @RequestMapping("/test")
    public String hhh() {
    	return "first";
	}
}

五、完整登录实例

这里写一个登录的实例,没有用Mybatis所以没有用Dao层,直接默认用户名为admin,密码为123456

//先写pojo类
package com.myw.pojo;

public class User {
    private Integer id;

    private String account;

    private String password;
    
    public User() {
        super();
    }

    public User(String account, String password) {
        this.account = account;
        this.password = password;
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getAccount() {
        return account;
    }

    public void setAccount(String account) {
        this.account = account == null ? null : account.trim();
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password == null ? null : password.trim();
    }
}

再写service层(虽然没有Dao层,但是所有的逻辑验证都应该放在service层)

//service的接口
package com.myw.service;

import com.myw.pojo.User;
import java.util.Map;

public interface IUserService {
    /**
     * 如果匹配成功,则返回user,否则返回null
     * @return
     */
    public User login(String account, String password);
}

//service的实现类(因为没有用mybatis所以mapper包为空)
package com.myw.service.Impl;

//import com.myw.mapper.UserMapper;
import com.myw.pojo.User;
import com.myw.service.IUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

@Service
public class UserServiceImpl implements IUserService {
    //@Autowired
    //private UserMapper um;

    @Override
    public User login(String account, String password) {
        //User user = um.selectByUserName(username);

        //如果用户名存在并且密码匹配
        if("admin".equals(account) && "123456".equals(password)){
            return new User(account,password);
        }
        
        return null;
    }
}

写web层

package com.myw.web;

import java.util.Map;
import com.myw.pojo.User;
import com.myw.service.IUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.servlet.http.HttpSession;

@RestController //现在jsp有点过时,一般是用ajax,所以直接使用RestController注解
public class UserController {
    @Autowired
    private IUserService us;

    @RequestMapping("login")
    public Map<String, Object> login(User user, HttpSession session){
        User u = us.login(user.getAccount(),user.getPassword());
        Map<String,Object> map = new HashMap<>(); 

        //如果用户成功登录,则将其添加到session中
        if(u != null){
            session.setAttribute("user",u);
            map.put("code",1);
        }else{
            map.put("code",0);
        }
        
        return map;
    }
}

前端部分:

//index.html(如果前端页面的名字和请求名一样,则会无法显示页面)
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>SpringMVCDemo</title>
        <script src="js/jquery.js"></script>
    </head>
    <body>
        用户名:<input type="text" id="account"/>
        密码:<input type="password" id="password"/>
        <input type="button" value="登录" onclick="login()"/>
    </body>
    <script>
        function login(){
            let account = $("#account").val();
            let password = $("#password").val();

            $.ajax({
                url:"login",
                type:"post",
                data:{"account":account,"password":password},
                dataType:"json",
                success:function (result){
                    console.log(result);

                    if(result.code==0){
                        alert("用户名或密码错误");
                        //location.href = "register.html";
                    }else{
                        alert("登录成功");
                    }
                }
            });
        }
    </script>
</html>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值