我被要求在现有的Web应用程序中创建一个报告(不是我自己的,我无法访问其代码)。我已经确定 JasperReports 是最简单的,因为周围有很多很好的例子......
我已经编写了下面的示例,但是浏览器显示一个空白页面,没有显示pdf。但是,如果我刷新浏览器页面,有时会显示pdf。
<%@ 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();
%>
我得到的确切错误是:
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]
现在,我知道问题出现在代码的最后几位
问题是,当我不允许在原始程序中添加类时,如何解决这个问题?
我只能添加 .jasper 文件,并通过神恩典添加一个简单的 .jsp 页面。
再次,我知道将代码添加到 jsp 是非常糟糕的形式,但我被困在这里......
答案 0 :(得分:0)
我昨天在JSP中创建并返回一个Excel文件时遇到了类似的错误。您需要删除结束(%&gt;)和打开(&lt;%)jsp标记之间的所有空格。
而不是
<%@ page contentType="application/pdf" %>
<%
Connection conn = null;
成功
<%@ page contentType="application/pdf" %><%
Connection conn = null;
如果你留空,那么JSP调用response.getOutputStream()来创建你不想要的JspWriter,因为你需要自己调用response.getOutputStream()来返回二进制文件。
答案 1 :(得分:0)
将我的代码更改为以下内容:
<%@ 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)
{
}
}
}
%>
不幸的不得不做这种方式,但至少是卓有成效....