Spring Mvc提交form表单上传文件

一、首先,我们要准备好form表单,代码示例如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<div class = "panel-body" >
     <form id = "firstUpdateForm" action= "/demo/upload/firstUpload" method= "post"
         enctype= "multipart/form-data" class = "form-horizontal" role= "form" target= "hidden_frame" >
         <div class = "modal-body" >
             <div class = "form-group" >
             <label class = "col-sm-3 control-label" >上传文件</label>
             <div class = "col-sm-5" >
                 <input type= "file" id= "firstDemoImgFile" name= "imgFile" >
             </div>
             </div>
         </div>
         <div class = "modal-footer" >
             <div id= "firstUploadSucceed" style= "display: none;" >
                 <strong>新增成功!</strong><span id= "firstUploadSucceedMsg" ></span>
             </div>
             <div id= "firstUploadFailed" style= "display: none;" >
                 <strong>对不起!新增失败</strong><span id= "firstUploadFailedMsg" ></span>
             </div>
             <button id= "createPeriadBtn" type= "submit" class = "btn btn-default" >确定 </button>
         </div>
     </form>
     <iframe name= 'hidden_frame' id= "hidden_frame" style= 'display:none' ></iframe>
</div>

这里先详细介绍一下该form表单里重要的东西:

  1. form表单提交的类型一定要加上enctype="multipart/form-data",这是提交媒体文件的声明
  2. form表单提交的target="hidden_frame",这是为了后台处理完成后返回结果刷新name为hidden_frame的iframe,这样就不会刷新当前页面了,大家可以对照上传文件系统演示,提交成功、失败会打印操作结果信息,就是利用这个实现的,模仿了ajax的方式,ajax是不能提交文件到后台的。
  3. 为了打印后台返回的结果,这个jsp文件需要引用一个js文件,uploadDemo.js,当controller返回操作结果后,会调用成功、失败的方法,在页面打印出结果,这里请和下面介绍的controller联系起来理解。

二、后台controller接收请求,代码示例如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
@Controller
@RequestMapping ( "/demo/upload" )
public class UploadController extends BaseController {
     
     @Autowired
     private UploadDemoService uploadDemoService;
     
     /**
      * 第一种Spring Mvc上传文件,提交form表单文件到一个frame,刷新该frame,页面打印出返回的结果
      * @param request
      * @param demo
      * @return
      */
     @RequestMapping (value = "firstUpload" , method = RequestMethod.POST)
     @ResponseBody
     public Object firstUpload(HttpServletRequest request, UploadDemoVo demo){
         logger.info( "firstUpload info:" + demo.toString());
         boolean flag = false ;
         //errorMessage:上传失败,则是错误信息;上传成功,则提示成功以及显示文件上传后的地址
         String errorMessage = ""
         try {
             flag = uploadDemoService.uploadForm(demo);
             errorMessage += "文件地址:http://demo.codingyun.com/demoFileDirectory/" + demo.getImgFile().getOriginalFilename();
         } catch (ServiceException serviceE){
             logger.error( "firstUpload failed!" , serviceE);
             errorMessage = serviceE.getMessage();
         } catch (Exception e){
             logger.error( "firstUpload failed!" , e);
             errorMessage = "新增文件失败!" ;
         }
         if (flag){
                 //上传成功,返回到前台,调用uploadSucced()这个方法
                         return "<script>window.parent.uploadSucced('" + errorMessage + "');</script>" ;
         }
         //上传失败,返回到前台,调用uploadFailed()这个方法
         return "<script>window.parent.uploadFailed('" + errorMessage + "');</script>" ;
     }
}

controller接收图片属性的实体类UploadDemoVo,源码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
public class UploadDemoVo {
     
     /**
      * 文件
      */
     private MultipartFile imgFile;
 
     public MultipartFile getImgFile() {
         return imgFile;
     }
 
     public void setImgFile(MultipartFile imgFile) {
         this .imgFile = imgFile;
     }
 
     @Override
     public String toString() {
         return "UploadDemoVo [imgFile=" + imgFile + "]" ;
     }
     
     public boolean validateFile() throws ServiceException{
         if (!ConstantUtil.fileTypeImg.contains( this .getImgFile().getContentType())){
             throw new ServiceException( "文件类型只能是jpeg、png!" );
         }
         if ( this .getImgFile().getSize() > 1000 * 100 ){
             throw new ServiceException( "文件最大不能超过100KB!" );
         }
         return true ;
     }
 
}


这里的controller我已经将注释写好,大家可以理解一下,若有不明白的可以随时在本页下方留言给我。

三、controller会调用后台service保存图片到服务器UploadDemoService,该service已经注入到controller中,源码如下:

这个是接口

1
2
3
4
5
6
7
8
9
10
public interface UploadDemoService {
     
     /**
      * 上传文件到指定路径
      * destinationDir 目标路径
      * 2014年6月10日
      */
     public boolean uploadFile(String destinationDir, MultipartFile file, String filename) throws Exception;
 
}

这个是接口的实现类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
@Service
public class UploadDemoServiceImpl implements UploadDemoService {
     
     @Override
     public boolean uploadForm(UploadDemoVo demo) throws Exception {
         demo.validateFile();
         uploadFile(
             "E:/test" , demo.getImgFile(), demo.getImgFile().getOriginalFilename());
         return true ;
     }
     
     private boolean uploadFile(String destinationDir, MultipartFile file, String filename)
             throws Exception {
          logger.info( "文件长度: " + file.getSize());
          logger.info( "文件类型: " + file.getContentType());
          logger.info( "文件名称: " + file.getName());
          logger.info( "文件原名: " + file.getOriginalFilename());
          logger.info( "========================================" );
          try {  
              SaveFileFromInputStream(file.getInputStream(), destinationDir, filename);  
          } catch (IOException e) {  
              logger.info(e.getMessage());  
              return false ;  
          }  
         return true ;
     }
     
      /**保存文件 
            * @param stream 
            * @param path 
            * @param filename 
            * @throws IOException 
          */ 
          private void SaveFileFromInputStream(InputStream stream,String path,String filename)
                throws IOException {        
                FileOutputStream outputStream = new FileOutputStream( path + "/" + filename);  
            int byteCount = 0 ;
            byte [] bytes = new byte [ 1024 ];
            while ((byteCount = stream.read(bytes)) != - 1 ){
                 outputStream.write(bytes, 0 , byteCount);
            }
            outputStream.close();  
            stream.close(); 
          }
 
}

四、测试效果

最后再跟大家说下,对照着上传文件系统演示,再看该文档会更容易理解,也更容易学会。如果大家有什么问题,请在底部留言,我会及时回复。


喜欢我的文章的,可以关注微信公众号“测试项目开发”,需要什么内容可以在里面提,我看到后会给大家解答。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值