Spring错误:IllegalStateException:在提交响应并且已调用getOutputStream()之后无法调用sendRedirect()

时间:2016-06-27 12:31:21

标签: spring spring-mvc spring-boot

当我尝试使用Spring boot和spring MVC下载压缩文件时出错: 错误:

  
      
  • SEVERE:servlet [dispatcherServlet]的Servlet.service()与path []的上下文发生异常[请求处理失败;嵌套异常是java.lang.IllegalStateException:无法在提交响应后调用sendRedirect()   java.lang.IllegalStateException:提交响应后无法调用sendRedirect()
  •   
  • SEVERE:servlet dispatcherServlet的Servlet.service()引发了异常   java.lang.IllegalStateException:已为此响应调用了getOutputStream()
  •   

基本上,我的应用程序正在加载文件,压缩它并下载新的zip文件。

这是我的应用程序控制器:

@Controller
public class ApplicationController {

    public String fileZipped;
    public String inputFile;

    @RequestMapping(method = RequestMethod.GET, value = "/uploadForm")
    public String provideUploadInfo() {
        return "uploadForm";
    }

    @RequestMapping(method = RequestMethod.POST, value = "/")
    public String handleFileUpload(@RequestParam("file") MultipartFile file,
                                   RedirectAttributes redirectAttributes,
                                   HttpServletResponse downloadResponse) {
        if (!file.isEmpty()) {
            try {
                inputFile = file.getOriginalFilename();
                BufferedOutputStream stream = new BufferedOutputStream(
                        new FileOutputStream(new File(Application.UPLOAD_DIR + "/" + inputFile)));
                FileCopyUtils.copy(file.getInputStream(), stream);
                stream.close();
                redirectAttributes.addFlashAttribute("message",
                        "You successfully uploaded " + file.getOriginalFilename() + "!");
                FileUtils.copyDirectory(Application.UPLOAD_DIR, Application.OUTPUT_FOLDER);
                FileUtils.cleanDirectory(new File(Application.UPLOAD_DIR));
            }
            catch (Exception e) {
                redirectAttributes.addFlashAttribute("message",
                        "You failed to upload " + file.getOriginalFilename() + " => " + e.getMessage());
            }
        }
        else {
            redirectAttributes.addFlashAttribute("message",
                    "You failed to upload " + file.getOriginalFilename() + " because the file was empty");
        }

        return "redirect:/zipFiles";
    }

    @RequestMapping(value = "/download")
    public String handleFileDownload(HttpServletResponse downloadResponse) throws IOException {
        InputStream inputStream = null;
        OutputStream outStream = null;
        try {
            if ( fileZipped!=null && Files.exists(Paths.get(fileZipped))) {
                inputStream = new FileInputStream(fileZipped);
                downloadResponse.setContentType(fileZipped);
                downloadResponse.addHeader("Content-Disposition", "attachment; filename=" + Paths.get(fileZipped).getFileName().toString());
                outStream = downloadResponse.getOutputStream();
                org.apache.commons.io.IOUtils.copy(inputStream, outStream);
                downloadResponse.flushBuffer();
            }
        } catch (IOException e) {
            throw new RuntimeException("IOError writing file to output stream");
        } finally {
            if (inputStream != null) inputStream.close();
            if (outStream != null) outStream.close();
        }
        return "redirect:/uploadForm";
    }

    @RequestMapping(value="/zipFiles")
    public String handleFileZip() throws IOException {
        if(inputFile!=null) {
            fileZipped = zipFiles(Application.OUTPUT_FOLDER, inputFile);
        }
        return "redirect:/download";
    }

    private String zipFiles(String folder, String zipFileName) throws IOException {

        String zipFile =  folder + "/" + FilenameUtils.removeExtension(zipFileName) + ".zip";
        FileOutputStream fileOutputstream = new FileOutputStream(zipFile);
        ZipOutputStream zipOutputStream = new ZipOutputStream(new BufferedOutputStream(fileOutputstream));

        File []filesArray = new File(folder).listFiles();
        for (File file : filesArray){
            if (!FilenameUtils.getExtension(file.getAbsolutePath()).equals("zip")) {
                byte[] buffer = new byte[1024];
                FileInputStream fileInputStream = new FileInputStream(file);
                zipOutputStream.putNextEntry(new ZipEntry(file.getName()));
                int length;
                while ((length = fileInputStream.read()) > 0) {
                    zipOutputStream.write(buffer, 0, length);
                }
                zipOutputStream.closeEntry();
                fileInputStream.close();
            }
        }
        zipOutputStream.close();
        return zipFile;
    }

如果我关闭输入和输出流,我不知道为什么会这样。

非常感谢你的帮助。

1 个答案:

答案 0 :(得分:0)

问题在于重定向。而不是

return "redirect:/uploadForm";

返回视图名称。

return "/uploadForm";