I have a view scoped bean where I create a person. A person can have a picture. This picture is uploaded the same page the person is created. The picture is not stored in a database or on disk (since the person isn't created yet). The bean has to be view scoped since a person can be created elsewhere and this uses the same bean. If the bean is session scoped and a user uploads a picture but does not save the person, the picture will be displayed next time the user tries to create a person.
I solved this by using two beans; one view scoped bean to create the person and a session scoped bean to upload the picture and to get the picture as a stream. This however causes the problem noted above.
How can I solve this in a better way?
The upload bean:
@ManagedBean(name = "uploadBean") @SessionScoped public class UploadBean { private UploadedFile uploadedFile; public UploadedFile getUploadedFile() { return uploadedFile; } public StreamedContent getUploadedFileAsStream() { if (uploadedFile != null) { return new DefaultStreamedContent(new ByteArrayInputStream(uploadedFile.getContents())); } return null; } public void uploadFile(FileUploadEvent event) { uploadedFile = event.getFile(); } } The create-a-person bean:
@ManagedBean(name = "personBean") @ViewScoped public class PersonBean { private Person newPerson = new Person(); public Person getNewPerson() { return newPerson; } private UploadedFile getUploadedPicture() { FacesContext context = FacesContext.getCurrentInstance(); ELContext elContext = context.getELContext(); UploadBean uploadBean = (UploadBean) elContext.getELResolver().getValue(elContext, null, "uploadBean"); return uploadBean.getUploadedFile(); } public void createPerson() { UploadedFile uploadedPicture = getUploadedPicture(); // Create person with picture; } } The relevant JSF page part:
<h:form enctype="multipart/form-data"> <p:outputPanel layout="block" id="personPicture"> <p:graphicImage height="150" value="#{uploadBean.uploadedFileAsStream}" rendered="#{uploadBean.uploadedFileAsStream != null}" /> </p:outputPanel> <p:fileUpload auto="true" allowTypes="/(\.|\/)(gif|jpe?g|png)$/" fileUploadListener="#{uploadBean.uploadedFile}" update="personPicture" /> <p:commandButton value="Save" actionListener="#{personBean.createPerson()}"/> </h:form>