Java 惰性地将JasperReports.jrxml编译为.jasper
我将Jasper报告与Spring框架提供的类一起使用。在创建Spring应用程序上下文时,此类负责将源.jrxml文件编译为编译后的.jasper格式 然而,这个编译过程实际上减慢了应用程序的启动时间。是否可以延迟编译报告,而不是在启动时编译,即仅在第一次请求时才编译报告 如果无法做到这一点,欢迎就如何缩短/消除报告编写时间提出其他建议。当然,我可以强制要求编译后的报告必须与.jrxml文件一起检入SVN,但在有人(很可能是我)忘记之前,这只是时间问题 干杯,Java 惰性地将JasperReports.jrxml编译为.jasper,java,spring,jasper-reports,Java,Spring,Jasper Reports,我将Jasper报告与Spring框架提供的类一起使用。在创建Spring应用程序上下文时,此类负责将源.jrxml文件编译为编译后的.jasper格式 然而,这个编译过程实际上减慢了应用程序的启动时间。是否可以延迟编译报告,而不是在启动时编译,即仅在第一次请求时才编译报告 如果无法做到这一点,欢迎就如何缩短/消除报告编写时间提出其他建议。当然,我可以强制要求编译后的报告必须与.jrxml文件一起检入SVN,但在有人(很可能是我)忘记之前,这只是时间问题 干杯, Don我和您一样,最初是为Jas
Don我和您一样,最初是为Jasper报告使用Spring助手类,但很快就放弃了它们,因为它们的粒度太粗,不够灵活,这在Spring中是不常见的。就像是事后才加上去的 我遇到的一个大问题是,一旦编译了它们,就需要appserver跳转才能放入新版本。在我的例子中,我正在寻找一个解决方案,通过这个解决方案,我可以在磁盘上更改它们,然后重新编译,就像JSP通常的工作方式一样(如果不关闭此功能,许多生产站点都会这样做) 或者,我希望能够将jrxml文件存储在数据库中或远程运行报告(例如通过jasperserverweb服务接口)。Spring类使得实现这些特性几乎是不可能的 所以我给你的建议是:自己滚。不过,在这一过程中,我会与大家分享一些小问题,以尽量减少痛苦。从文档中看,有些事情并不明显 您首先需要的是jasper reports编译器。它负责将jrxml文件编译成JasperDesign对象。有几种实现方式,但您需要的是JRJdtCompiler。您可以在Spring应用程序上下文中实例化并注入它。避免使用其他类似beanshell编译器的工具,因为将报表作为大型beanshell脚本运行并不是特别快或高效(在我了解更多之前,我就发现了这一点) 您需要包含JRJdtCompiler的jar文件。我认为Jasper Reports dist的完整版本包括这个罐子。这是一个eclipse产品 您可以将JasperDesign存储在任何您喜欢的地方(HttpSession、servlet上下文或任何内容)。fillReport()方法是您感兴趣的主要方法。它创建一个JasperPrint对象,它是运行报告的一个实例。参数只是作为映射传入的 现在,要在HTML、PDF等格式中创建版本号,需要将其导出。您可以使用像JRHtmlExporter和JRPdfExporter这样的类来实现这一点。它们需要某些参数。最棘手的是HTML导出器,因为HTML显然不包含图像。Jasper包含一个ImageServlet类,该类从会话(JRHtmlExporter将它们放在会话中)获取这些内容,但是您必须正确地配置HTML导出器和图像servlet,并且很难判断哪里出了问题 我不记得它的具体细节,但在中有一个例子,我强烈建议您在任何时候都可以购买该产品。50美元相当便宜。你也可以获得年度订阅,但在我看到的18个多月里,我没有看到任何变化。如果你需要的话,只要买新版本就行了(你可能不会买)
希望这有帮助。报告在第一次运行时编译,请在AbstractJasperReportsView保护的最终JasperReport loadReport(资源)方法中设置断点以确认这一点 但是,上面的文章是正确的,如果您想提供任何特定的编译过程,您需要扩展JasperReportsMultiFormatView 动态编译的一个很好的例子如下: }
import net.sf.jasperreports.engine.JasperReport;
import org.apache.log4j.Logger;
import org.springframework.web.servlet.view.jasperreports.JasperReportsMultiFormatView;
public class DynamicJasperReportsMultiFormatView extends JasperReportsMultiFormatView {
private static final Logger LOG = Logger.getLogger(DynamicJasperReportsMultiFormatView.class);
/**
* The JasperReport that is used to render the view.
*/
private JasperReport jasperReport;
/**
* The last modified time of the jrxml resource file, used to force compilation.
*/
private long jrxmlTimestamp;
@Override
protected void onInit() {
jasperReport = super.getReport();
try {
String url = getUrl();
if (url != null) {
jrxmlTimestamp = getApplicationContext().getResource(url).getFile().lastModified();
}
} catch (Exception e) {
e = null;
}
}
@Override
protected JasperReport getReport() {
if (this.isDirty()) {
LOG.info("Forcing recompilation of jasper report as the jrxml has changed");
this.jasperReport = this.loadReport();
}
return this.jasperReport;
}
/**
* Determines if the jrxml file is dirty by checking its timestamp.
*
* @return true to force recompilation because the report xml has changed, false otherwise
*/
private boolean isDirty() {
long curTimestamp = 0L;
try {
String url = getUrl();
if (url != null) {
curTimestamp = getApplicationContext().getResource(url).getFile().lastModified();
if (curTimestamp > jrxmlTimestamp) {
jrxmlTimestamp = curTimestamp;
return true;
}
}
} catch (Exception e) {
e = null;
}
return false;
}