美文网首页
第四章 SpringBoot整合Web开发(二)

第四章 SpringBoot整合Web开发(二)

作者: shenyoujian | 来源:发表于2019-05-05 10:44 被阅读0次

    一、文件上传

    • springmvc对文件上传做了简化,springboot做了更近一步的简化,使文件上传更加方便。
    • java中的文件上传涉及到两个组件,一个是CommonsMultipartResolver,另一个是StandardServletMultipartResolver,第一个是使用commons-fileupload来处理multipart请求(需要添加commons-fileupload的jar包),第二个是基于servlet3.0来处理multipart请求的,tomcat7中就已经支持servlet3.0,而springboot2.0内置tomcat8,所以springboot不需要添加额外的jar包就能实现文件上传功能。
    • springboot提供的文件上传的配置类类MultipartAutoConfiguration默认也是使用StandardServletMultipartResolver。

    二、实战

    2.1 单文件上传
    • 创建springboot项目,而不是maven项目
    • 导入依赖spring-boot-starter-web 依赖
    • 在resource的static目录里创建一个upload.html
    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    </head>
    <body>
    <form method="post" action="/upload" enctype="multipart/form-data">
        <input type="file" name="uploadFile" value="选择文件">
        <input type="submit" value="上传">
    </form>
    
    </body>
    </html>
    
    • 接口
    /**
     * @Author ljs
     * @Description 上传文件
     * @Date 2019/4/26 17:12
     **/
    @RestController
    public class FileUploadController {
    
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd");
    
        @RequestMapping("/upload")
        public String upload(MultipartFile uploadFile, HttpServletRequest request){
            //1、上传文件保存路径为项目运行目录下的uploadFile文件夹,并在文件夹中通过日期对所上传的文件归类保存
            String realPath = request.getSession().getServletContext().getRealPath
                    ("/uploadFile/");
    
    
            String format = sdf.format(new Date());
            File folder = new File(realPath + format);
            if(!folder.isDirectory()){
                folder.mkdirs();
            }
            //2.给上传的文件重命名避免重名
            String oldName = uploadFile.getOriginalFilename();
            String newName = UUID.randomUUID().toString() + oldName.substring
                    (oldName.lastIndexOf("."), oldName.length());
            try{
                //3.保存操作
                uploadFile.transferTo(new File(folder, newName));
                //4.生成上传文件的访问路径,并将路径返回
                String filePath = request.getScheme() + "://" + request
                        .getServerName() + ":" + request.getServerPort() +
                        "/uploadFile/" + format + "/" + newName;
                return filePath;
            } catch (IOException e) {
                e.printStackTrace();
            }
            return "上传失败";
        }
    }
    
    
    • 运行


      image.png
      image.png
    • 是保存在项目运行目录下的,之前访问静态资源有5个路径,其中一个/就是运行目录下,所以可以直接访问。
    • 对图片上传细节的一些设置,基本上不用,只要关注上传逻辑就行。


      image.png
    2.2 多文件上传
    • 创建uploads.html
    <body>
    <form action="/uploads" method="post" enctype="multipart/form-data">
        <input type="file" name="uploadFiles" value="请选择文件">
        <input type="file" name="uploadFiles" value="请选择文件">
        <input type="submit" value="上传">
    </form>
    
    • controller,就是套一个for循环
    @PostMapping("/uploads")
        public String uploads(MultipartFile[] uploadFiles, HttpServletRequest req) {
            for (MultipartFile uploadFile : uploadFiles) {
                String realPath = req.getSession().getServletContext().getRealPath("/uploadFile/");
                System.out.println(realPath);
                String format = sdf.format(new Date());
                File folder = new File(realPath + format);
                if (!folder.isDirectory()) {
                    folder.mkdirs();
                }
                String oldName = uploadFile.getOriginalFilename();
                String newName = UUID.randomUUID().toString() + oldName.substring(oldName.lastIndexOf("."), oldName.length());
                try {
                    uploadFile.transferTo(new File(folder, newName));
                    String filePath = req.getScheme() + "://" + req.getServerName() + ":" + req.getServerPort() + "/uploadFile/" + format + newName;
    //            return filePath;
                    System.out.println(filePath);
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            return "上传失败!";
        }
    
    
    • 运行


      image.png
      image.png

    三、@ControllerAdvice

    • @ControllerAdvice 主要用来处理全局数据,主要搭配@ExceptionHandler、@ModelAttribute 以及@InitBinder来使用。
    3.1 全局异常处理
    • @ControllerAdvice配合@ExceptionHandler定义全局异常捕获机制。例如上传文件超过了限制的大小就会抛出异常。
    • 定义全局异常捕获的步骤
      1. 定义一个CustomExceptionHandler类,加上@ControllerAdvice注解,表明这个类会被扫描到spring容器中。
      2. 接着开始定义处理各种异常的方法,例如uploadException,加上@ExceptionHandler(MaxUploadSizeExceededException.class),表明该方法来处理MaxUploadSizeExceededException类型异常。如果想处理所有异常,把MaxUploadSizeExceededException换成Exception即可。方法的参数可以有异常实例、HttpServletResponse、HttpServletRequest 以及Model ,返回值可以是 JSON,ModelAndView 和一个逻辑视图名等。
    /**
     * @Author ljs
     * @Description 全局异常捕获
     * @Date 2019/4/27 20:29
     **/
    
    @ControllerAdvice
    public class CustomExceptionHandler {
    
        @ExceptionHandler(MaxUploadSizeExceededException.class)
        public void uploadException(MaxUploadSizeExceededException e,
                                    HttpServletResponse resp) throws IOException {
            resp.setContentType("text/html;charset=utf-8");
            PrintWriter out = resp.getWriter();
            out.write("上传文件大小超出限制!");
            out.flush();
            out.close();
        }
    }
    
    • 跟着之前的
    3.2 添加全局数据

    @ControllerAdvice配合@ModelAttribute可以进行全局数据配置。
    全局配置类GlobalConfig添加userInfo方法,返回一个Map,其中info表示key,map表示value。

    @ControllerAdvice
    public class GlobalConfig {
        @ModelAttribute(value = "info")
        public Map<String, String> userInfo(){
            HashMap<String, String> map = new HashMap<>();
            map.put("username", "李建生");
            map.put("gender", "男");
            return map;
        }
    }
    

    相关文章

      网友评论

          本文标题:第四章 SpringBoot整合Web开发(二)

          本文链接:https://www.haomeiwen.com/subject/binfnqtx.html