问题描述
- jasperreport+applet实现客户端打印报表
-
本人使用ireport5.1.0画的报表,实现客户端打印时报java.io.StreamCorruptedException:invalid stream header:0D0A0D0A这个错误,下面是代码,请各位高手帮忙看看怎么回事:
1)、action类代码
import java.io.File;
import java.io.ObjectOutputStream;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.HashMap;
import java.util.Map;import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;import net.sf.jasperreports.engine.JRResultSetDataSource;
import net.sf.jasperreports.engine.JasperFillManager;
import net.sf.jasperreports.engine.JasperPrint;import org.apache.struts2.ServletActionContext;
import com.opensymphony.xwork2.ActionSupport;
public class IreportAction extends ActionSupport{
private static final long serialVersionUID = 1974082731836773155L;
private static final String CONTENTTYPE = "application/octet-stream";/** * 打印报表 * @return */ @SuppressWarnings("unchecked") public void doIreportPrint(){ HttpServletResponse response = ServletActionContext.getResponse(); String fileName = ""; String sql = "select id,dname,dcode from ct_su_departments where datalevel = 0 and status = 0 and rownum <=100"; //建立连接 Connection conn = this.createConnection(); //参数设置 Map parameters = new HashMap(); try { Statement stmt = conn.createStatement();//获取数据库链接 ResultSet rs = stmt.executeQuery(sql);//获取数据 String jasper = new File(ServletActionContext.getServletContext().getRealPath("/report/report1.jasper")).getPath();//获取文件的绝对路径 JasperPrint jpt = JasperFillManager.fillReport(jasper, parameters, new JRResultSetDataSource(rs));//匹配数据源,生成JasperPrint response.setContentType(CONTENTTYPE); ServletOutputStream ouputStream = response.getOutputStream(); ObjectOutputStream oos = new ObjectOutputStream(ouputStream); oos.writeObject(jpt); oos.flush(); oos.close(); }catch(Exception e) { System.out.println("Error:" + e.toString()); e.printStackTrace(); }finally { CloseConnect(conn); conn = null; } } /** * 建立数据库连接 * @return */ public Connection createConnection(){ Connection conn; try{ String driver = "oracle.jdbc.driver.OracleDriver";//oracle.jdbc.OracleDriver String url = "jdbc:oracle:thin:@172.19.24.239:1521:NSOA"; Class.forName(driver); conn = DriverManager.getConnection(url,"JXKHOA","JXKHOA"); conn.setAutoCommit(false); return conn; }catch(SQLException e1) { System.out.println("建立连接错误 = " + e1.toString()); e1.printStackTrace(); }catch(ClassNotFoundException e2) { System.out.println("建立连接错误 = " + e2.toString()); e2.printStackTrace(); } return null; } /** * 关闭数据库连接 * @param conn */ public void CloseConnect(Connection conn){ try{ conn.commit(); conn.setAutoCommit(true); conn.close(); }catch(Exception e){ System.out.println("关闭连接错误 = " + e.toString()); } }
}
2)japplet代码:
import java.io.PrintWriter;
import java.io.StringWriter;
import java.net.URL;import javax.swing.JOptionPane;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperPrintManager;
import net.sf.jasperreports.engine.util.JRLoader;public class IreportApplet extends javax.swing.JApplet{
private static final long serialVersionUID = 2525694418170444107L;private URL url = null; private JasperPrint jasperPrint = null; public void init(){ String strUrl = "http://172.19.24.28:8100/BaseWeb/ireportPrint.action"; if (strUrl != null){ try{ URL urll = new URL(strUrl); url = urll; System.out.println("url="+urll); }catch (Exception e){ StringWriter swriter = new StringWriter(); PrintWriter pwriter = new PrintWriter(swriter); e.printStackTrace(pwriter); JOptionPane.showMessageDialog(this, swriter.toString()); } }else{ JOptionPane.showMessageDialog(this, "init():Source URL not specified"); } } public void start(){ if (url != null){ if (jasperPrint == null){ try{ jasperPrint = (JasperPrint)JRLoader.loadObject(url); }catch (Exception e){ StringWriter swriter = new StringWriter(); PrintWriter pwriter = new PrintWriter(swriter); e.printStackTrace(pwriter); JOptionPane.showMessageDialog(this, swriter.toString()); } } if (jasperPrint != null){ final JasperPrint print = jasperPrint; Thread thread = new Thread(new Runnable(){ public void run(){ try{ System.out.println("进入start方法,即将打印pdf文件"); JasperPrintManager.printReport(print, true); }catch (Exception e){ StringWriter swriter = new StringWriter(); PrintWriter pwriter = new PrintWriter(swriter); e.printStackTrace(pwriter); JOptionPane.showMessageDialog(null, swriter.toString()); } } }); thread.start(); }else{ JOptionPane.showMessageDialog(this, "Empty report."); } }else{ JOptionPane.showMessageDialog(this, "start():Source URL not specified"); } }
}
执行到jasperPrint = (JasperPrint)JRLoader.loadObject(url);这就话是就报错了。该报表导出excel和pdf都是可以的,而且在action类里面直接使用JasperViewer.viewReport(jpt,false);也是可以打印的,就这个japplet生成客户端打印时报错了。希望各位高手能赐教,非常感谢!!!
解决方案
新建一 web 项目 Test2。将 iReport 目录 lib 下的所有 jar 包导入。在 servlet 程序中把从数据库得到的数据传入 *.jrxml 文件得到 *.jrprint 文件(这才是我们想要的东西),并把这个对象写入 Stream流,以返还给请求客户端。源码:
?
view plainprint?
package?com.defo......
答案就在这里:Applet+客户端打印+jasperreport+报表