rog*_*til 1 file-io jsf file-upload jsf-2.2
我正在尝试使用h:inputFile标记上传图像文件并将其写入磁盘.
我的JSF代码:
<h:form id="fileUploadForm" enctype='multipart/form-data' prependId="false">
<h:inputFile value="#{solicitacaoManagedBean.imagemCarregada}" />
<br />
<h:commandButton styleClass="btn btn-primary " value="Enviar" action="#{solicitacaoManagedBean.enviarImagem}" />
</h:form>
Run Code Online (Sandbox Code Playgroud)
我的ManagedBean:
@Named(value = "solicitacaoManagedBean")
@SessionScoped
@MultipartConfig(location = "/home/rogerio/tmp/")
public class SolicitacaoManagedBean implements Serializable {
private Part imagemCarregada;
Run Code Online (Sandbox Code Playgroud)
(......)
public void enviarImagem() throws IOException {
try {
imagemCarregada.write("teste.jpg");
} catch (IOException ioe) {
System.out.println("Erro ao escrever: " + ioe.getLocalizedMessage());
}
}
}
Run Code Online (Sandbox Code Playgroud)
据推测,方法write将项目上传到磁盘,IOException也不会被抛出/捕获.
该@javax.servlet.annotation.MultipartConfig注释应该被放置在类执行HttpServlet,而不是在一个支撑类.基本上,该注释必须放在FacesServlet类上,这是自JSF 2.2以来已经完成的.
换句话说,@MultipartConfig您的支持bean类上的注释被忽略并且没有任何效果,并且该文件实际上没有保存在location注释中指定的您.相反,它被保存在相对于所谓的当前工作目录的路径中,该目录基本上是当前正在java.exe执行的"当前打开的文件夹" .对于Java Web应用程序,通常是服务器的二进制文件夹.您可以按如下方式跟踪它:
System.out.println(new File(".").getAbsolutePath());
Run Code Online (Sandbox Code Playgroud)
你会在那里看到你上传的文件.
此外,即使@MultipartConfig注释确实有效,该location属性实际上也不代表永久文件上载保存位置.相反,它表示上载文件大小超过可用/已配置内存空间时的临时磁盘存储位置.您永远不应将上传的文件永久存储在标识的位置@MultipartConfig(location).您应该始终通过Part#getInputStream()并获取文件内容并将其写入由新的File或Path表示绝对路径提供的所需永久位置.
摆脱整个@MultipartConfig注释.它在支持bean类中没有做任何有用的事情.只需获取文件内容Part#getInputStream()并将其复制到所需的绝对路径:
try (InputStream input = imagemCarregada.getInputStream()) {
Files.copy(input, new File("/home/rogerio/tmp/teste.jpg").toPath());
}
Run Code Online (Sandbox Code Playgroud)
与具体问题无关,为此目的使用会话范围的bean并不理想.而是使用视图或请求范围.另请参见如何选择正确的bean范围?并且,prependId="false"建议不要将其用于除登录框架之外的其他用途,该登录框架不支持请求参数名称中的JSF前置ID.另请参见UIForm with prependId ="false"break <f:ajax render>.
| 归档时间: |
|
| 查看次数: |
7316 次 |
| 最近记录: |