用JasperReport无非就是要导出报表。
下面写了一个接口和几种类型的报表文件导出方法
接口:ReportExporter
|--------抽象类,JasperReportBaseExporter(基本实现,设置通用参数)
|--------图片:JasperReportGraphics2DExporter
|--------页面:JasperReportHtmlExporter
|-------- PDF:JasperReportPdfExporter
|--------XLS:JasperReportXlsExporter
为了编码简单为JasperReport写了接口:
ReportExporter:
package com.zhr.report.exporter;
import java.io.IOException;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.JasperPrint;
public interface ReportExporter {
/**
* 不同的exporter设置不同的属性
*
* @param jasperPrint
* @param request
* @param response
* @throws IOException
*/
public void setExporterParameters(JasperPrint jasperPrint,
HttpServletRequest request, HttpServletResponse response)
throws IOException;
/**
* 导出
*
* @param request
* @param response
* @param jrxmlName
* jrxml名称(classpath下) xxx.jrxml
* @param parameters
* @param jrdataSource
* @param fileName
* 另存文件名
* @param encodingType
* 编码方式
* @throws JRException
* @throws IOException
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource,
String fileName, String encodingType) throws JRException,
IOException;
/**
* 导出
*
* @param request
* @param response
* @param jrxmlName
* jrxml名称(classpath下) xxx.jrxml
* @param parameters
* @param jrdataSource
* @param fileName
* 另存文件名
* @throws JRException
* @throws IOException
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource,
String fileName) throws JRException, IOException;
/**
* 导出
*
* @param request
* @param response
* @param jrxmlName
* jrxml名称(classpath下) xxx.jrxml
* @param parameters
* @param jrdataSource
* @throws JRException
* @throws IOException
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource)
throws JRException, IOException;
}
JasperReportBaseExporter
package com.zhr.report.exporter.impl;
import java.io.IOException;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.JRExporter;
import net.sf.jasperreports.engine.JRExporterParameter;
import net.sf.jasperreports.engine.JasperCompileManager;
import net.sf.jasperreports.engine.JasperFillManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperReport;
import net.sf.jasperreports.engine.util.JRLoader;
import net.sf.jasperreports.j2ee.servlets.ImageServlet;
import com.zhr.report.exporter.ReportExporter;
public abstract class JasperReportBaseExporter implements ReportExporter {
/**
* 编码方式
*/
public String encodingType = "utf-8";
/**
* 保存文件名
*/
public String fileName = "NoTitle";
public JRExporter exporter;
/**
* 设置页面类型
*
* @param response
* @param fileName
* @param encodingType
*/
public void setContentTypeByType(HttpServletResponse response,
String fileName, String encodingType) {
this.encodingType = encodingType;
setContentTypeByType(response, fileName);
}
/**
* 设置页面类型
*
* @param response
* @param fileName
*/
public void setContentTypeByType(HttpServletResponse response,
String fileName) {
this.fileName = fileName;
setContentType(response);
}
/**
* 将报表jrxml文件编译成jasper文件
*
* @param root_path
* 项目根目录
* @param jrxmlPath
* jrxml名称(classpath下) xxx.jrxml
* @return
* @throws JRException
*/
protected String compileJrxmlFile(String jrxmlPath) throws JRException {
String _jrxmlPath = this.getClass().getClassLoader().getResource(
jrxmlPath).getFile();
if (_jrxmlPath.startsWith("/")) {
_jrxmlPath = _jrxmlPath.substring(1);
}
String jasperPath = _jrxmlPath.replace(".jrxml", ".jasper");
JasperCompileManager.compileReportToFile(_jrxmlPath, jasperPath);
return jasperPath;
}
/**
* 获得 JasperPrint对象
*
* @param jasperPath
* .jasper文件路径
* @param parameters
* @param jrdataSource
* @return
* @throws JRException
*/
protected JasperPrint getJasperPrint(String jasperPath,
Map<String, Object> parameters, JRDataSource jrdataSource)
throws JRException {
JasperReport report;
JasperPrint jasperPrint;
// 载入报表jasper文件 获得 JasperReport对象
report = (JasperReport) JRLoader.loadObject(jasperPath);
// 根据报表对象(JasperReport),报表所需参数(parameters)以及报表数据源(JRDataSource) 获得报表打印器
jasperPrint = JasperFillManager.fillReport(report, parameters,
jrdataSource);
return jasperPrint;
}
/*
* (non-Javadoc)
*
* @see
* com.ekupeng.report.exporter.ReportExporter#setExporter(net.sf.jasperreports
* .engine.JRExporter, net.sf.jasperreports.engine.JasperPrint,
* javax.servlet.http.HttpServletRequest,
* javax.servlet.http.HttpServletResponse)
*/
public void setExporterParameters(JasperPrint jasperPrint,
HttpServletRequest request, HttpServletResponse response)
throws IOException {
// 为报表导出器设置报表打印器
this.exporter.setParameter(JRExporterParameter.JASPER_PRINT,
jasperPrint);
// 为报表导出器设置输出流(从HttpResponse中获得OutputStream流)
this.exporter.setParameter(JRExporterParameter.OUTPUT_STREAM, response
.getOutputStream());
/**
* 将报表打印器放置到HttpSession中 否则在ImageServlet中会找不到JasperPrint对象
* ImageServlet中会根据JasperPrint输出图片
*/
request.getSession().setAttribute(
ImageServlet.DEFAULT_JASPER_PRINT_SESSION_ATTRIBUTE,
jasperPrint);
this.setExporterParameters();
}
/*
* (non-Javadoc)
*
* @see
* com.ekupeng.report.exporter.ReportExporter#exporter(javax.servlet.http
* .HttpServletRequest, javax.servlet.http.HttpServletResponse,
* java.lang.String, java.util.Map,
* net.sf.jasperreports.engine.JRDataSource, java.lang.String,
* java.lang.String)
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource,
String fileName, String encodingType) throws JRException,
IOException {
this.encodingType = encodingType;
exporter(request, response, jrxmlName, parameters, jrdataSource,
fileName);
}
/*
* (non-Javadoc)
*
* @see
* com.ekupeng.report.exporter.ReportExporter#exporter(javax.servlet.http
* .HttpServletRequest, javax.servlet.http.HttpServletResponse,
* java.lang.String, java.util.Map,
* net.sf.jasperreports.engine.JRDataSource, java.lang.String)
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource,
String fileName) throws JRException, IOException {
this.fileName = fileName;
exporter(request, response, jrxmlName, parameters, jrdataSource);
}
/*
* (non-Javadoc)
*
* @see
* com.ekupeng.report.exporter.ReportExporter#exporter(javax.servlet.http
* .HttpServletRequest, javax.servlet.http.HttpServletResponse,
* java.lang.String, java.util.Map,
* net.sf.jasperreports.engine.JRDataSource)
*/
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource)
throws JRException, IOException {
this.setContentType(response);
String jasperPath = compileJrxmlFile(jrxmlName);
if (null == jrdataSource) {
throw new JRException("JRDataSource is null!");
}
JasperPrint jasperPrint = getJasperPrint(jasperPath, parameters,
jrdataSource);
this.setExporterParameters(jasperPrint, request, response);
this.exporter.exportReport();
}
/**
* 不同的exporter设置不同的属性
*
* @throws IOException
*/
protected abstract void setExporterParameters() throws IOException;
/**
* 设置页面类型
*
* @param response
*/
protected abstract void setContentType(HttpServletResponse response);
public String getEncodingType() {
return encodingType;
}
public void setEncodingType(String encodingType) {
this.encodingType = encodingType;
}
public String getFileName() {
return fileName;
}
public void setFileName(String fileName) {
this.fileName = fileName;
}
}
JasperReportGraphics2DExporter
package com.zhr.report.exporter.impl;
import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.Map;
import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.JRExporterParameter;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.export.JRGraphics2DExporter;
import net.sf.jasperreports.engine.export.JRGraphics2DExporterParameter;
public class JasperReportGraphics2DExporter extends JasperReportBaseExporter{
private BufferedImage bufferedImage;
public JasperReportGraphics2DExporter() throws JRException {
this.exporter = new JRGraphics2DExporter();
}
@Override
protected void setContentType(HttpServletResponse response) {
response.setCharacterEncoding(this.encodingType);
response.setContentType("image/jpeg");
}
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource)
throws JRException, IOException {
this.setContentType(response);
String jasperPath = compileJrxmlFile(jrxmlName);
if (null == jrdataSource) {
throw new JRException("JRDataSource is null!");
}
JasperPrint jasperPrint = getJasperPrint(jasperPath, parameters,
jrdataSource);
this.setExporterParameters(jasperPrint, request, response);
this.exporter.exportReport();
this.bufferedImage.getGraphics().dispose();
ImageIO.write(bufferedImage, "JPEG", response.getOutputStream());
}
public void setExporterParameters(JasperPrint jasperPrint,
HttpServletRequest request, HttpServletResponse response)
throws IOException {
//图片显示倍数
float zoom_ratio = Float.valueOf(2);
// 为报表导出器设置报表打印器
this.exporter.setParameter(JRExporterParameter.JASPER_PRINT,
jasperPrint);
//创建一个影像对象
this.bufferedImage = new BufferedImage(jasperPrint.getPageWidth() * (int)zoom_ratio, jasperPrint.getPageHeight() * (int)zoom_ratio, BufferedImage.TYPE_INT_RGB);
//取graphics
Graphics2D g = (Graphics2D) bufferedImage.getGraphics();
//设置相应参数信息
exporter.setParameter(JRGraphics2DExporterParameter.GRAPHICS_2D, g);
exporter.setParameter(JRGraphics2DExporterParameter.ZOOM_RATIO, zoom_ratio);
}
@Override
protected void setExporterParameters() throws IOException {
}
}
JasperReportHtmlExporter
注:在导出html的时候需要在web.xml中配置ImageServlet
要求JRHtmlExporterParameter.IMAGES_URI的值与Servlet匹配(红色标记)
如,
<servlet>
<servlet-name>ImageServlet</servlet-name>
<servlet-class>net.sf.jasperreports.j2ee.servlets.ImageServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>ImageServlet</servlet-name>
<url-pattern>/image</url-pattern>
</servlet-mapping>
package com.zhr.report.exporter.impl;
import java.io.File;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.export.JRHtmlExporter;
import net.sf.jasperreports.engine.export.JRHtmlExporterParameter;
public class JasperReportHtmlExporter extends JasperReportBaseExporter {
public JasperReportHtmlExporter(){
this.exporter = new JRHtmlExporter();
}
@Override
protected void setContentType(HttpServletResponse response) {
response.setCharacterEncoding(this.encodingType);
response.setContentType("text/html");
}
@Override
protected void setExporterParameters() throws IOException {
//图片请求servlet
this.exporter.setParameter(JRHtmlExporterParameter.IMAGES_URI,"/image?image=");
//自定义页头
this.exporter.setParameter(JRHtmlExporterParameter.HTML_HEADER, "");
//自定义页尾
this.exporter.setParameter(JRHtmlExporterParameter.HTML_FOOTER, "");
//是否保存图片到目录,并提供路径
this.exporter.setParameter(JRHtmlExporterParameter.IS_OUTPUT_IMAGES_TO_DIR, true);
this.exporter.setParameter(JRHtmlExporterParameter.IMAGES_DIR, new File("d:\\jsprp"));
//是否需要图片来对齐
this.exporter.setParameter(JRHtmlExporterParameter.IS_USING_IMAGES_TO_ALIGN,false);
//是否忽略页面边距
this.exporter.setParameter(JRHtmlExporterParameter.IGNORE_PAGE_MARGINS,true);
}
}
JasperReportXlsExporter
package com.zhr.report.exporter.impl;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.export.JRXlsExporter;
import net.sf.jasperreports.engine.export.JRXlsExporterParameter;
public class JasperReportXlsExporter extends JasperReportBaseExporter {
public JasperReportXlsExporter(){
this.exporter = new JRXlsExporter();
}
@Override
protected void setContentType(HttpServletResponse response) {
response.setCharacterEncoding(this.encodingType);
response.setContentType("application/vnd.ms-excel");
response.setHeader("Content-Disposition", "attachment; filename="
+ this.fileName + ".xls");
}
@Override
protected void setExporterParameters() throws IOException {
this.exporter.setParameter(
JRXlsExporterParameter.IS_REMOVE_EMPTY_SPACE_BETWEEN_ROWS,
Boolean.TRUE);
this.exporter.setParameter(
JRXlsExporterParameter.IS_ONE_PAGE_PER_SHEET, Boolean.FALSE);
this.exporter.setParameter(
JRXlsExporterParameter.IS_WHITE_PAGE_BACKGROUND, Boolean.FALSE);
}
}
JasperReportPdfExporter
package com.zhr.report.exporter.impl;
import java.io.IOException;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.JasperExportManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.export.JRPdfExporter;
public class JasperReportPdfExporter extends JasperReportHtmlExporter {
public JasperReportPdfExporter() {
this.exporter = new JRPdfExporter();
}
protected void setContentType(HttpServletResponse response) {
response.setCharacterEncoding(this.encodingType);
response.setContentType("application/pdf");
response.setHeader("Content-Disposition", "attachment; filename="
+ this.fileName + ".pdf");
}
@Override
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource)
throws JRException, IOException {
setContentType(response);
String jasperPath = compileJrxmlFile(jrxmlName);
JasperPrint jasperPrint = getJasperPrint(jasperPath, parameters,
jrdataSource);
JasperExportManager.exportReportToPdfStream(jasperPrint, response
.getOutputStream());
}
public void exporter(HttpServletRequest request,
HttpServletResponse response, String jrxmlName,
Map<String, Object> parameters, JRDataSource jrdataSource,
String fileName) throws JRException, IOException {
this.fileName = fileName;
exporter(request, response, jrxmlName, parameters, jrdataSource);
}
}
jrxml文件:
<?xml version="1.0" encoding="UTF-8"?>
<jasperReport xmlns="http://jasperreports.sourceforge.net/jasperreports" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://jasperreports.sourceforge.net/jasperreports http://jasperreports.sourceforge.net/xsd/jasperreport.xsd" name="report name" pageWidth="950" pageHeight="290" columnWidth="910" leftMargin="20" rightMargin="20" topMargin="20" bottomMargin="20">
<property name="ireport.zoom" value="1.0"/>
<property name="ireport.x" value="0"/>
<property name="ireport.y" value="0"/>
<parameter name="monthOfYear" class="java.lang.String"/>
<parameter name="xName" class="java.lang.String"/>
<parameter name="yName" class="java.lang.String">
<defaultValueExpression><![CDATA["num"]]></defaultValueExpression>
</parameter>
<parameter name="sql" class="java.lang.String"/>
<queryString>
<![CDATA[SELECT 'a' type, DATE(gmt_created) date,COUNT(*)num FROM table GROUP BY DATE(gmt_created)]]>
</queryString>
<field name="type" class="java.lang.String"/>
<field name="date" class="java.util.Date"/>
<field name="num" class="java.lang.Long"/>
<summary>
<band height="250" splitType="Stretch">
<lineChart>
<chart theme="default">
<reportElement stretchType="RelativeToTallestObject" mode="Transparent" x="0" y="0" width="910" height="250"/>
<chartTitle/>
<chartSubtitle/>
<chartLegend position="Bottom"/>
</chart>
<categoryDataset>
<categorySeries>
<seriesExpression><![CDATA[$F{type}]]></seriesExpression>
<categoryExpression><![CDATA[($F{date}.getMonth() + 1 ) + "-" + $F{date}.getDate()]]></categoryExpression>
<valueExpression><![CDATA[$F{num}]]></valueExpression>
</categorySeries>
</categoryDataset>
<linePlot isShowLines="true" isShowShapes="true">
<plot labelRotation="-30.0">
<seriesColor seriesOrder="0" color="#0099FF"/>
<seriesColor seriesOrder="1" color="#66FF66"/>
<seriesColor seriesOrder="2" color="#FF0033"/>
<seriesColor seriesOrder="3" color="#FFFF33"/>
</plot>
<categoryAxisLabelExpression><![CDATA[$P{xName} == null || $P{xName}.equals( "" ) ? "" : $P{xName}]]></categoryAxisLabelExpression>
<categoryAxisFormat labelRotation="-30.0">
<axisFormat labelColor="#000000" tickLabelColor="#333333" axisLineColor="#000000">
<labelFont/>
<tickLabelFont/>
</axisFormat>
</categoryAxisFormat>
<valueAxisLabelExpression><![CDATA[$P{yName} == null || $P{yName}.equals( "" ) ? "" : $P{yName}]]></valueAxisLabelExpression>
<valueAxisFormat>
<axisFormat labelColor="#000000" tickLabelColor="#000000" verticalTickLabels="false" axisLineColor="#000000">
<labelFont/>
<tickLabelFont/>
</axisFormat>
</valueAxisFormat>
</linePlot>
</lineChart>
</band>
</summary>
</jasperReport>
下面写一个简单的测试:
package com.ekupeng.core.action;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import com.zhr.report.exporter.ReportExporter;
import com.zhr.report.service.PolygramReportService;
import com.zhr.report.model.report.Polygram;
@Controller
public class ReportAction {
@Autowired
private PolygramReportService polygramReportService;
@Autowired
@Qualifier("jasperReportGraphics2DExporter")
private ReportExporter exporter;
@RequestMapping("/front/core/activity/report/**/{id}")
public void countReport(HttpServletRequest request,HttpServletResponse response,
@PathVariable("id") Long id,String type,Long day) {
List<Polygram> beans = new ArrayList<Polygram>();
String typeName = "";
if("GET".equalsIgnoreCase(type)){
beans = polygramReportService.selectCWPostageSoldByDate(id ,day);
typeName = "销量";
}else if("USE".equalsIgnoreCase(type)){
//USE
beans = polygramReportService.selectCWPostageUseByDate(id ,day);
typeName = "使用";
}else{
//VIEW
beans = polygramReportService.selectCWPostageViewByDate(id ,day);
typeName = "访客";
}
for (Polygram Polygram : beans) {
Polygram.setType(typeName);
}
//报表中需要的参数
Map<String, Object> parameters = new HashMap<String, Object>();
parameters.put("monthOfYear", "8");
parameters.put("xName", "日期");
parameters.put("yName", typeName);
try {
export(request, response, beans, "report/testPerMonth.jrxml",parameters);
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 根据jrxml,数据源和jrxml需要的模版参数
* @param <T>
* @param request
* @param response
* @param datas
* @param jrxmlName
* @param parameters
* @throws IOException
* @throws JRException
*/
private <T> void export(HttpServletRequest request,
HttpServletResponse response, List<T> datas, String jrxmlName, Map<String, Object> parameters)
throws IOException, JRException {
JRDataSource jrdataSource = new JRBeanCollectionDataSource(datas);
exporter.exporter(request, response, jrxmlName, parameters,
jrdataSource);
}
}