锐单电子商城 , 一站式电子元器件采购平台!
  • 电话:400-990-0325

SpringMVC入门

时间:2023-01-22 22:00:00 28zjw印制板连接器

1.什么是MVC?

MVC根据模型、视图、控制器对软件架构的理念进行划分。

其中的M:Model,模型层,指的是JavaBean,用于数据处理。

其中javabean有两种:

一是实体类Bean,用于存储数据,如常见数据User类,student类;

二是处理业务。Bean,一般指工程Service或Dao处理业务逻辑和数据访问的对象。

V:View,视图层是与用户互动的页面,显示数据等。html页面或jsp页面。

C:Controller,工程中的控制层servlet,用于接受请求和响应结果。

MVC结构执行流程如下图所示:

2.什么是SpringMVC?

SpringMVC是Spring框架的一个分支,该springMVC框架的主要功能是接收浏览器的请求响应,处理数据,然后返回页面显示,可以理解为和Servlet同样的工作。

3.为什么要用?SpringMVC?

我们在使用Servlet处理,需要做的是接收参数,业务处理,返回结果(页面跳转或返回JSON数据)。其中各Servlt除了不同的业务处理,接收参数和返回结果是相同的,所以我们可以包装这两个功能,SpringMVC就帮我们完成了这样的封装,因此SpringMVC也是对Servlet优化。

4.如何使用SpringMVC

(1)使用IDEA创建maven-web项目,点击File->new->project->选择maven->按图示勾选->next->填写项目名称,完成创建。

项目创建完成后,需要自动生成web.xml替换文件内容如下:

  

(2)引入springmvc依赖

              org.springframework       spring-webmvc       5.2.15.RELEASE        

(3)将DispatcherServlet注册到web.xml文件上

                     DispactherServlet         org.springframework.web.servlet.DispatcherServlet                      contextConfigLocation                          classpath:springmvc.xml                            DispactherServlet         /      

(4)创建springmvc.xml配置文件

我们选择在main->resources该文件在目录下创建,创建方法如下图所示(注:项目自动生成的目录中没有java和resources目录,需要手动创建)。

这里需要注意的是,如果没有引入,springmvc依赖不会出现Spring Config选项。

(5)写入包扫描的配置信息

            

(6)创建controller设置访问名称,在服务器上部署项目后,通过访问"hello01"访问此方法。

//该注释标记为处理层,有此注释,springmvc会根据配置信息对该类进行扫描 @Controller  public class HelloController {      ///将此方法上映射请求路径。通过这条路径访问这种方法     @RequestMapping(value = "/hello01")      public String hello01(){         System.out.println("业务处理");          return "hello01.jsp"; //响应页面     } }

5.SpringMVC操作流程;

(1)根据上述配置,客户端有请求http://localhost:8080/springmvc01/hello01;

(2) 来到tomcat服务器。

(3)springmvc前端控制器DipatcherServlet接受所有请求。

(4)查看您的请求地址和哪个地址@RequestMaping匹配。

(5) 执行对应的方法。方法会返回一个字符串。springmvc将字符串分析为要转发的网页。

(6)通过视图解析器拼接字符串。

(7)获取拼接地址,找到相应的网页。

(8) 向客户渲染网页

6.如何在controller层接收请求参数

(1)接收少量参数时,可采用相同的方法形参数和请求参数名完成参数的接收

(2)当接收到的参数数量较大时,如提交表单数据,我们可以包装实体类接收这些参数

注意:

由于浏览器的默认编码和idea默认编码是可能的一致,将会出现乱码的问题,这里就需要通过编码过滤器来解决该问题,这里我们可以自定义过滤器,来完成编码的过滤;但是自己编写的过滤器,需要注意一点,jdk1.8之前的版本需要重写接口中的init和destory方法,而jdk1.9及以后则不需要重写这两个方法。

        除了自定义过滤器外,springmvc也为我们提供了一个过滤器,我们只需要在web.xml文件中添加配置信息则可以进行使用:

    
        EncodingFilter
        org.springframework.web.filter.CharacterEncodingFilter
        
            
            encoding
            UTF-8
        
    
    
        EncodingFilter
        /*
    

(3)当接受的参数含有日期类型时,则可以在时间类型的属性上添加@DateTimeFormat(pattern="yyyy-MM-dd"),并在springmvc.xml配置文件中开启特殊注解驱动:
 

    
    
    
    

    
    

7.如何将controller层的数据返回页面并展示

在servlet中返回浏览器的数据可以存储在request、session中,而springmvc中的controller也就相当于servlet的功能,因此我们也可以将数据存储在request和session中,在浏览器中通过:EL表达式。${scope.key} 来获取存储的数据,但是当使用request时,则将数据与服务器进行了绑定,数据安全性会降低,因此springmvc提供了一个Model类来存储返回的数据,但是该类存储的返回默认为request,需要通过注解@SessionAttributes(value = {"user"})来将该key值设置为session范围。

8.使用重定向跳转

 @RequestMapping("list5")
    public String list5(){
        System.out.println("使用了重定向跳转!");
        //在返回的页面前添加redirect:字样,springmvc则会进行重定向跳转
        return "redirect:list.jsp"; 
    }

9.springmvc如何返回json数据?

(1)在我们实现异步请求、ajax请求时都要求我们返回json数据

(2)在Servlet中我们通过FastJson,手动将java数据转化为json数据,同时需要将our.print(json)输出json数据,并需要将out进行关闭。

(3)而springmvc不需要我们手动进行json数据的转换,它内置了一个jackson的jar来实现json数据的转化;

9.1引入jackson依赖


    
      com.fasterxml.jackson.core
      jackson-databind
      2.13.2.2
    

9.2 引入依赖后的执行

当返回的数据为javabean对象时,该jar包则会自动将该对象数据转化为json数据。

注意:若返回的对象中包含时间属性,则需要在该属性上添加@JsonFormat(pattern="yyyy-MM-dd")注解,否则所显示的值为从1970年至数据值之间的毫秒数。

10.springmvc的全局异常处理

在执行各类方法时可能会遇到各种异常,而且可能会有多种方法出现相同的异常,我们可以通过一个全局异常处理的操作,对各种方法中的异常进行处理,避免异常处理代码的反复编写。

如何使用全局异常处理?

(1)创建一个异常类:并在类前添加 @ControllerAdvice注解

//表示该为类controller的异常处理类
@ControllerAdvice 
public class AllExceptinHandle {

        //当发生RuntimeException就会触发该方法
     @ExceptionHandler(value = RuntimeException.class) 
     public String error01(){
         return "error01.jsp";
     }
    //当发生Exception就会触发该方法
    @ExceptionHandler(value = Exception.class) 
    public String error02(){
        return "error02.jsp";
    }
}

(2)在springmvc.xml配置文件中的包扫描部分添加上该类所在包的路径;

(3)在工程运行过程中如果发生对应异常,则会跳转到该类中,执行对应异常处理的方法。

11.springmvc的拦截器

过滤器: 过滤掉某些资源,

拦截器只会拦截controller层的资源路径。

 使用拦截器:

(1)创建类,实现HandlerInterceptor接口

public class InterceptorOne implements HandlerInterceptor {

    //拦截器的处理方法。
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("经过了该拦截器");
        
        //该方法的返回值为布尔类型,其中true:表示该拦截器放行 false:则不放行
        return true;
    }
}

(2)将该拦截器注册到springmvc配置文件中


    
        
            
            
            
            
            
            
            
            
        
    

12.文件上传

文件上传的原理:一般来说,将文件上传后,数据库中存储的应该是该文件的访问路径,而当我们需要使用该数据时,根据数据库中所存储的文件访问路径继续该文件的使用。

12.1 文件上传至本地服务器

(1)引入文件上传依赖

    
    
      commons-fileupload
      commons-fileupload
      1.4
    

(2)创建页面,并通过表单中的标签进行文件选择

    <%--
      method: 提交方式 文件上传必须为post提交。
      enctype:该属性的默认值为application/x-www-form-urlencoded 表示提交的表单数据不能包含文件数据
              multipart/form-data:可以包含文件数据

      input的type属性必须为file类型,而且必须有name属性
   --%>
   

(3)在springmvc.xml配置文件中添加文件上传解析器

    
     
          
          
     

(4)创建upload01方法

//注意:MultipartFile 参数名必须和中name属性相同
    @RequestMapping("/upload01")
    public String upload01(MultipartFile myfile, HttpServletRequest request) throws Exception{

        //(1)得到本地服务目录的地址
        String path = request.getSession().getServletContext().getRealPath("upload");
        //(2)判断该目录是否存在
        File file=new File(path);
        if(!file.exists()){
             file.mkdirs();
        }
        //(3)//把myfile保存到本地服务中某个文件夹下。 可使用UUID工具类来自动生成一段不重复的字符串,来作为文件的名称
        String filename= UUID.randomUUID().toString().replace("-","")+myfile.getOriginalFilename();
        File target=new File(path+"/"+filename);
        myfile.transferTo(target); //把myfile转移到目标目录下
        return "";
    }

12.2结合elementui、vue、axios实现文件上传

(1)页面布局,可从elementui官网组件获取(elementUI组件https://element.eleme.io/#/zh-CN/component/installation

<%@ page contentType="text/html;charset=UTF-8" language="java" %>


    Title
    
    
    
    
    
    
    
    


    
<%--action:文件上传的路径--%>

(2)后台接口

与普通上传到本地文件类似,但是需要将文件所在地址返回给页面用图片文件的回显。

//创建返回结果类,用于存储返回结果
//使用lombok插件可通过以下三个注解实现get、set方法以及有参无参构造方法的建立
@Data
@NoArgsConstructor
@AllArgsConstructor
public class CommonResult {
    private Integer code;
    private String msg;
    private Object data;
}



    @RequestMapping("/upload02")
    @ResponseBody
    public CommonResult upload01(MultipartFile file, HttpServletRequest request) throws Exception{
        String path = request.getSession().getServletContext().getRealPath("upload");
        File thisFile = new File(path);
        if (!thisFile.exists()){
            thisFile.mkdirs();
        }
        String fileName = UUID.randomUUID().toString().replace("-", "")+file.getOriginalFilename();
        File newFile = new File(path+"/"+fileName);
        file.transferTo(newFile);
        
        //返回文件所在地址
        return new CommonResult(100,"上传成功","http://localhost:8080/SpringMVC10/upload/"+fileName);
    }

12.3上传文件到远程文件服务器(这里我使用的是,OSS阿里云服务器)

12.3.1 为什么需要使用远程文件服务器?

文件上传到本地时,有两个缺点,第一就是若不进行配置,所上传的文件会在本地服务器重启时被删除掉。

第二,如果搭建集群的情况下,文件将不能够在集群中共享。

想解决以上的两个问题,就可以通过远程服务器来实现,这样在集群模式下,可以让多个服务器都能够访问这个远程服务器,来实现文件的存取。

12.3.2 如何使用阿里云OSS对象存储实现远程文件上传

阿里云https://www.aliyun.com/?accounttraceid=42bce330710e4d96b294aaae23000be8hjou

(1)注册阿里云账号

此处略过

(2)找到对象存储OSS

(3)开通对象存储OSS服务 

(4) 开通后进入控制台,创建Bucket(可以理解为你的文件所存储的位置)

 

 需要变动的仅有读写权限,其余的默认即可

(5)申请阿里云密钥

我们需要使用密钥来通过java代码来访问OSS。

 这里需要进行验证,验证通过后

 (4)使用idea进行文件上传到阿里云oss

前端页面

<%@ page contentType="text/html;charset=UTF-8" language="java" %>


    Title
    <%--引入css样式--%>
    
    <%--引入vue--%>
    
    
    
    
    




 后端接口实现

    @RequestMapping("/uploadToOSS")
    @ResponseBody
    public CommonResult uploadToOSS(MultipartFile file, HttpServletRequest request) throws Exception{

        String endpoint = "oss-cn-hangzhou.aliyuncs.com";
        // 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。
        String accessKeyId = 自己的密钥id";
        String accessKeySecret = "自己的密钥密码";
        // 填写Bucket名称,例如examplebucket。
        String bucketName = "com-zjw";
        // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。
        String nowTime = new SimpleDateFormat("yyyy/MM/dd").format(new Date());

        String fileName = nowTime+"/"+UUID.randomUUID().toString().replace("-", "")+file.getOriginalFilename();
        String objectName = fileName;

        // 创建OSSClient实例。
        OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);


        try {
            InputStream inputStream = file.getInputStream();
            // 创建PutObject请求。
            ossClient.putObject(bucketName, objectName, inputStream);
        }
        finally {
            if (ossClient != null) {
                ossClient.shutdown();
            }
        }
        String url = "https://"+bucketName+"."+endpoint+"/"+objectName;
        //String url = endpoint.replace("//","//"+bucketName+".")+"/"+objectName;
        System.out.println(url);
        return new CommonResult(100,"上传成功",url);
    }

 这样写我们会发现,如果我们需要进行多次文件上传的话,就需要书写很多的重复代码,为了解决这个问题,我们可以抽取出一个工具类,在接口的实现方法中直接调用,简化我们的接口实现方法

public class UploadFileUntil {

    public static String upload(MultipartFile file) throws IOException {
        String endpoint = "oss-cn-hangzhou.aliyuncs.com";
        // 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。
        String accessKeyId = "自己的密钥id";
        String accessKeySecret = "自己的密钥密码";
        // 填写Bucket名称,例如examplebucket。
        String bucketName = "com-zjw";
        // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。
        String nowTime = new SimpleDateFormat("yyyy/MM/dd").format(new Date());

        String fileName = nowTime+"/"+ UUID.randomUUID().toString().replace("-", "")+file.getOriginalFilename();
        String objectName = fileName;

        // 创建OSSClient实例。
        OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);


        try {
            InputStream inputStream = file.getInputStream();
            // 创建PutObject请求。
            ossClient.putObject(bucketName, objectName, inputStream);
        }
        finally {
            if (ossClient != null) {
                ossClient.shutdown();
            }
        }
        String url = "https://"+bucketName+"."+endpoint+"/"+objectName;
        return url;
    }
}

 这样我们的接口实现方法就会简化很多

    @RequestMapping("/uploadAvatar")
    public CommonResult upalodAvatar(MultipartFile file){
        try {
            String url = UploadFileUntil.upload(file);
            return new CommonResult(100,"上传成功",url);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return new CommonResult(100,"上传失败",null);
    }

(5)带用户头像的表单提交

前端代码

<%@ page contentType="text/html;charset=UTF-8" language="java" %>


    添加用户
    
    <%--引入vue--%>
    
    
    
    
    



    
提交

接口实现方法

@RestController
public class UserController {

    @RequestMapping("/uploadAvatar")
    public CommonResult upalodAvatar(MultipartFile file){
        try {
            String url = UploadFileUntil.upload(file);
            return new CommonResult(100,"上传成功",url);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return new CommonResult(100,"上传失败",null);
    }
    @PostMapping("/addUser")
    public CommonResult addUser(@RequestBody User user){
        System.out.println(user);
        return new CommonResult(100,"添加成功",null);
    }
}

两个接口一个实现头像上传的功能,并且将图片的url传给前端界面,回显在页面上,并且给表单数据的imageUrl赋值,在表单的提交方法中,将数据传给controller层,之后与数据库交互,将数据存储到数据库中。

(6)补充的零散内容

@RestController

类上等价于 @COntroller+@ResponseBody,该注解下所有的方法都是返回json数据
@RequestMapping: 作用: 把请求路径映射到响应的方法上。

 @RequestParam(value = "u"):设置你接受的请求参数名。查询参数

@RequestMapping(value = "/addUser",method = RequestMethod.POST)
       method:表示该接口接受的请求方式.不设置可以接受任意请求方式

@GetMapping("addUser"):表示只接受get提交方式的请求     

@RequestBody:把请求的json数据转换为java对象。从前端到后端

@ResponseBody:把java转换为json数据   从后端转前端

锐单商城拥有海量元器件数据手册IC替代型号,打造电子元器件IC百科大全!

相关文章