用JSF下载文件?

时间:2010-08-06 21:46:51

标签: java jsf download

这是使用JSF下载文件的正确方法?只是放置文件的链接?在那种情况下我如何获得文件URL?

我见过一个使用BufferedInputStream的例子:

http://www.winstonprakash.com/articles/jsf/file_download_link.htm

有什么区别?

由于

3 个答案:

答案 0 :(得分:24)

如果它是一个简单的文件,只需放在公共webcontent(放置静态和JSF文件的地方)并创建一个链接。

<h:outputLink value="/files/file.ext">link</h:outputLink>

servletcontainer会担心应用正确的标头。

如果由于某些特定原因(例如,在服务器计算机或数据库中的固定路径中)位于公共webcontent之外,则创建一个获取InputStream的servlet并将其写入{ {3}}至少在Content-TypeContent-DispositionContent-Length标题中的回复。您可以找到OutputStream一个简单的启动示例。此外,它可以简单地链接到servlet的url-pattern

如果它是动态生成的并且取决于JSF特定的请求参数,那么您也可以在受h:commandLinkh:commandButton约束的托管bean操作中执行此操作,但您只需要确保在bean的操作方法结束时调用here以防止JSF手动导航。可以重用相同类型的servlet代码来传输文件。您可以在FacesContext#responseComplete()中找到启动示例。

答案 1 :(得分:13)

我需要制作类似的代码来通过JSF下载文件

这是我的JSF页面中的下载按钮

<h:commandButton value="Download" action="#{helloBean.downloadFile}" />

这是我的Java代码

public void downloadFile() {

    File file = new File("/home/marco/file.txt");
    HttpServletResponse response = (HttpServletResponse) FacesContext.getCurrentInstance().getExternalContext().getResponse();  

    response.setHeader("Content-Disposition", "attachment;filename=file.txt");  
    response.setContentLength((int) file.length());  
    ServletOutputStream out = null;  
    try {  
        FileInputStream input = new FileInputStream(file);  
        byte[] buffer = new byte[1024];  
        out = response.getOutputStream();  
        int i = 0;  
        while ((i = input.read(buffer)) != -1) {  
            out.write(buffer);  
            out.flush();  
        }  
        FacesContext.getCurrentInstance().getResponseComplete();  
    } catch (IOException err) {  
        err.printStackTrace();  
    } finally {  
        try {  
            if (out != null) {  
                out.close();  
            }  
        } catch (IOException err) {  
            err.printStackTrace();  
        }  
    }  

}

答案 2 :(得分:-1)

我的错误

FacesContext.getCurrentInstance().getResponseComplete(); 

的类型

java.lang.IllegalStateException: getOutputStream() has already been called for this response 

我解决了它:

JSF页面:

<h:commandButton action="#{bean.downloadFile}" id="downloadBtn" value="Download"/>

Bean方法:

public void downloadFile(File file) {   
    FacesContext facesContext = FacesContext.getCurrentInstance();
    HttpServletResponse response = (HttpServletResponse) facesContext.getExternalContext().getResponse();
    response.setHeader("Content-Disposition", "attachment;filename=file.txt");
    response.setContentLength((int) file.length());
    FileInputStream input= null;
    try {
        int i= 0;
        input = new FileInputStream(file);  
        byte[] buffer = new byte[1024];
        while ((i = input.read(buffer)) != -1) {  
            response.getOutputStream().write(buffer);  
            response.getOutputStream().flush();  
        }               
        facesContext.responseComplete();
        facesContext.renderResponse();
    } catch (IOException e) {
        e.printStackTrace();
    } finally {
        try {
            if(input != null) {
                input.close();
            }
        } catch(IOException e) {
            e.printStackTrace();
        }
    }
}