1

I use the media primefaces tag to present pdf's but if the bean is @ViewScope the stream is always null, why?

nuno
  • 1,693
  • 1
  • 16
  • 47
Marin
  • 960
  • 1
  • 9
  • 35

2 Answers2

4

Because the desired JSF view state isn't available when the webbrowser is about to download the PDF in an entirely separate(!!) HTTP request. This is essentially exactly the same problem as with PrimeFaces <p:graphicImage> as answered in the following questions:

Basically, you need to pass an identifier of the desired media file as <f:param> and then create an entirely stateless managed bean which streams the desired DefaultStreamedContent depending on the current request phase ID and the supplied request parameter.

Community
  • 1
  • 1
BalusC
  • 992,635
  • 352
  • 3,478
  • 3,452
  • This works fine on Opra, Edge, Chrome BUT NOT ON FIREFOX 60.0.2 - `Caused by: org.apache.catalina.connector.ClientAbortException: java.io.IOException`, why this is happening? – UHDante Oct 04 '18 at 08:19
  • OK -> https://stackoverflow.com/a/43163279/9112160 Solved my first problem, now I have on Firefox that `context.getCurrentPhaseId() == PhaseId.RENDER_RESPONSE` is always the same "6", no entering on the else to charge the data :( – UHDante Oct 04 '18 at 09:45
  • SOLVED -> https://support.mozilla.org/en-US/kb/use-adobe-reader-view-pdf-files-firefox. Seams my firefox wasent prepare to view PDF, by default it wanted to download... – UHDante Oct 04 '18 at 11:11
-2

JSF/Primefaces 7.0 -

@Named
@ViewScope
public class FileBean implements Serializable {
    private String _DIR="/path/to/dir";

    public StreamedContent getImage(String fileName) throws IOException {
        FacesContext context = FacesContext.getCurrentInstance();
        if (context.getCurrentPhaseId() == PhaseId.RENDER_RESPONSE) {
            return new DefaultStreamedContent();
        } else {
            File f = new File(_DIR, filename);
            return new DefaultStreamedContent(new FileInputStream(f));          
        }
    }
}

And use stream="false" in you p:graphicImage tag:

<p:graphicImage value="#{fileBean.image}" stream="false" cache="false"></p:graphicImage>

JSF/Primefaces 8.0

@Named
@RequestScoped
public class GraphicImageView {
    private StreamedContent chart; 
    @PostConstruct
    public void init() {
        try { 

            chart = DefaultStreamedContent.builder()
                    .contentType("image/png")
                    .stream(() -> {
                        try {
                            JFreeChart jfreechart = ChartFactory.createPieChart("Cities", createDataset(), true, true, false);
                            File chartFile = new File("dynamichart");
                            ChartUtilities.saveChartAsPNG(chartFile, jfreechart, 375, 300);
                            return new FileInputStream(chartFile);
                        }
                        catch (Exception e) {
                            e.printStackTrace();
                            return null;
                        }
                    })
                    .build();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    public StreamedContent getChart() {
        return chart;
    }

}

In you front page use this line:

<p:graphicImage value="#{graphicImageView.chart}" />

Check link: https://www.primefaces.org/showcase/ui/multimedia/graphicImage.xhtml

Y. sellami
  • 19
  • 4