简体   繁体   中英

In jsp, generating pdf I get a java.lang.IllegalStateException: STREAM

I've been asked to create a report in an existing webapplication (not my own, and I do not have access to its code). I've decided that JasperReports was the easiest, since there are many fine examples around...

I've written the sample below, but the browser displays an empty page, no pdf is showing. However, if I refresh the browser page, sometimes the pdf is shown.

<%@ page  import="java.io.*"%> 
<%@ page  import="javax.servlet.*"%>
<%@ page  import="java.sql.Connection"%>
<%@ page  import="java.sql.DriverManager"%>
<%@ page  import="java.util.HashMap"%>
<%@ page  import="java.util.Map"%>
<%@ page  import="javax.servlet.ServletException"%>
<%@ page  import="javax.servlet.ServletOutputStream"%>
<%@ page  import="net.sf.jasperreports.engine.*"%>
<%@ page contentType="application/pdf" %>


    <%
         Connection conn = null;
        try {
            Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver");
            conn = DriverManager.getConnection("jdbc:sqlserver://[server][\instance]:1433;databaseName=[databasename];integratedSecurity=True");
        } catch (Exception ex) {
            ex.printStackTrace();


        }


        File reportFile = new File(application.getRealPath("/bespoke/rapport/Planning.jasper"));//your report_name.jasper file
        Map parameters = new HashMap();
        byte[] bytes = JasperRunManager.runReportToPdf(reportFile.getPath(), parameters, conn);


                response.setContentType("application/pdf");
                response.setContentLength(bytes.length);
                ServletOutputStream outputStream = response.getOutputStream();
                outputStream.write(bytes, 0, bytes.length);
                outputStream.flush();
                outputStream.close();

           %>

The exact error I'm getting is:

java.lang.IllegalStateException: STREAM
at org.mortbay.jetty.Response.getWriter(Response.java:616) ~[jetty-6.1.24.jar:6.1.24]
at javax.servlet.ServletResponseWrapper.getWriter(ServletResponseWrapper.java:122) ~[servlet-api-2.5-20081211.jar:na]
at org.apache.jasper.runtime.JspWriterImpl.initOut(JspWriterImpl.java:187) ~[jsp-2.1-glassfish-2.1.v20091210.jar:na]
at org.apache.jasper.runtime.JspWriterImpl.flushBuffer(JspWriterImpl.java:180) ~[jsp-2.1-glassfish-2.1.v20091210.jar:na]

Now, I know the issue is in the last bits of code.
Problem is, how do I solve this when I am not allowed to add classes to the original program?
I can only add the .jasper file and by gods grace a simple .jsp page.
Again, I know it is extremely bad form to add code to a jsp , but I am stuck here...

I got a similar error yesterday with creating and returning an Excel file in JSP. You need to remove all the space between your closing (%>) and opening (<%) jsp tags.

Instead of

 <%@ page contentType="application/pdf" %>


 <%
  Connection conn = null;

Make it

 <%@ page contentType="application/pdf" %><%
  Connection conn = null;

If you leave space then JSP calls the response.getOutputStream() to create the JspWriter, which you don't want since you need to call response.getOutputStream() yourself to return the binary file.

Changed my code to the following:

<%@ page language="java" import="net.sf.jasperreports.engine.*,net.sf.jasperreports.engine.export.*" %>  
<%@ page import="org.apache.commons.lang.time.*" %>  
<%@ page import="java.sql.*,java.io.*" %>
<%
 String filename = request.getParameter("filename");
 String reporttype = request.getParameter("reporttype");
 Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver");
 Connection conn = DriverManager.getConnection("jdbc:sqlserver://[servername]\\[instancename];databaseName=[databasename][:portnumber(remove when dynamic port is used)];integratedSecurity=True");
           System.out.println("Connection Established");
 String path = application.getRealPath("/");

 JasperPrint jasperPrint = JasperFillManager.fillReport(path + "/" + filename, null, conn);
 System.out.println("Report Created...");

 OutputStream ouputStream = response.getOutputStream();

 JRExporter exporter = null;

 if( "pdf".equalsIgnoreCase(reporttype) )
 {
      response.setContentType("application/pdf");
      exporter = new JRPdfExporter();
      exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint);
      exporter.setParameter(JRExporterParameter.OUTPUT_STREAM, ouputStream);
 }
 else if( "html".equalsIgnoreCase(reporttype) )
 {
      exporter = new JRHtmlExporter();
      exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint);
      exporter.setParameter(JRExporterParameter.OUTPUT_STREAM, ouputStream);
 }
 else if( "xls".equalsIgnoreCase(reporttype) )
 {
      response.setContentType("application/xls");
      response.setHeader("Content-Disposition", "inline; filename=\"file.xls\"");

      exporter = new JRXlsExporter();
      exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint);
      exporter.setParameter(JRExporterParameter.OUTPUT_STREAM, ouputStream);
 }
 try 
 {
      exporter.exportReport();
 } 
 catch (JRException e) 
 {
      throw new ServletException(e);
 }
 finally
 {
      if (ouputStream != null)
      {
           try
           {
                ouputStream.close();
           }
           catch (IOException ex)
           {
           }
      }
 }
%>  

Sad to have to do it this way, but at least it does the trick....

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM