abstractjasperreportsview.java
来自「一个关于Spring框架的示例应用程序,简单使用,可以参考.」· Java 代码 · 共 526 行 · 第 1/2 页
JAVA
526 行
throw new ApplicationContextException("'reportDataKey' for main report is required when specifying a value for 'subReportDataKeys'");
}
this.subReports = new HashMap(this.subReportUrls.size());
for (Enumeration urls = this.subReportUrls.propertyNames(); urls.hasMoreElements();) {
String key = (String) urls.nextElement();
String path = this.subReportUrls.getProperty(key);
Resource resource = getApplicationContext().getResource(path);
this.subReports.put(key, loadReport(resource));
}
}
if (this.headers == null) {
this.headers = new Properties();
}
if (!this.headers.containsKey(HEADER_CONTENT_DISPOSITION)) {
this.headers.setProperty(HEADER_CONTENT_DISPOSITION, CONTENT_DISPOSITION_INLINE);
}
}
/**
* Convert the given fully qualified field name to a corresponding
* JRExporterParameter instance.
*
* @param fqFieldName the fully qualified field name, consisting
* of the class name followed by a dot followed by the field name
* (e.g. "net.sf.jasperreports.engine.export.JRHtmlExporterParameter.IMAGES_URI")
* @return the corresponding JRExporterParameter instance
*/
protected JRExporterParameter convertToExporterParameter(String fqFieldName) {
int index = fqFieldName.lastIndexOf('.');
if (index == -1 || index == fqFieldName.length()) {
throw new IllegalArgumentException("Parameter name [" + fqFieldName + "] is not a valid static field. " +
"The parameter name must map to a static field such as " +
"net.sf.jasperreports.engine.export.JRHtmlExporterParameter.IMAGES_URI");
}
String className = fqFieldName.substring(0, index);
String fieldName = fqFieldName.substring(index + 1);
try {
Class cls = ClassUtils.forName(className);
Field field = cls.getField(fieldName);
if (JRExporterParameter.class.isAssignableFrom(field.getType())) {
try {
return (JRExporterParameter) field.get(null);
}
catch (IllegalAccessException ex) {
throw new IllegalArgumentException("Unable to access field [" + fieldName + "] of class [" + className + "]." +
" Check that it is static and accessible.");
}
}
else {
throw new IllegalArgumentException("Field [" + fieldName + "] on class [" + className +
"] is not assignable from JRExporterParameter - check the type of this field.");
}
}
catch (ClassNotFoundException ex) {
throw new IllegalArgumentException("Class [" + className + "] in key [" + fqFieldName + "] could not be found.");
}
catch (NoSuchFieldException ex) {
throw new IllegalArgumentException("Field [" + fieldName + "] in key [" + fqFieldName +
"] could not be found on class [" + className + "].");
}
}
/**
* Loads a <code>JasperReport</code> from the specified <code>Resource</code>. If
* the <code>Resource</code> points to an uncompiled report design file then the
* report file is compiled dynamically and loaded into memory.
*
* @param resource the <code>Resource</code> containing the report definition or design
* @return a <code>JasperReport</code> instance
*/
private JasperReport loadReport(Resource resource) throws ApplicationContextException {
try {
String fileName = resource.getFilename();
if (fileName.endsWith(".jasper")) {
// load pre-compiled report
if (logger.isInfoEnabled()) {
logger.info("Loading pre-compiled Jasper Report from " + resource);
}
return (JasperReport) JRLoader.loadObject(resource.getInputStream());
}
else if (fileName.endsWith(".jrxml")) {
// compile report on-the-fly
if (logger.isInfoEnabled()) {
logger.info("Compiling Jasper Report loaded from " + resource);
}
JasperDesign design = JRXmlLoader.load(resource.getInputStream());
return getReportCompiler().compileReport(design);
}
else {
throw new IllegalArgumentException("Report URL [" + getUrl() + "] must end in either .jasper or .jrxml");
}
}
catch (IOException ex) {
throw new ApplicationContextException("Could not load JasperReports report for URL [" + getUrl() + "]", ex);
}
catch (JRException ex) {
throw new ApplicationContextException("Could not parse JasperReports report for URL [" + getUrl() + "]", ex);
}
}
/**
* Return the JasperReports compiler to use for compiling a ".jrxml"
* file into a a report class. Default is <code>JRBshCompiler</code>,
* which requires BeanShell on the class path.
*
* @see net.sf.jasperreports.engine.design.JRCompiler
* @see net.sf.jasperreports.engine.design.JRBshCompiler
*/
protected JRCompiler getReportCompiler() {
return new JRBshCompiler();
}
/**
* Finds the report data to use for rendering the report and then invokes the
* <code>renderReport</code> method that should be implemented by the subclass.
*
* @param model the model map, as passed in for view rendering. Must contain
* a report data value that can be converted to a <code>JRDataSource</code>,
* acccording to the <code>getReportData</code> method.
* @see #getReportData
*/
protected void renderMergedOutputModel(Map model, HttpServletRequest request, HttpServletResponse response)
throws Exception {
response.setContentType(getContentType());
// Determine JRDataSource for main report.
JRDataSource dataSource = getReportData(model);
if (this.subReports != null) {
// Expose sub-reports as model attributes.
model.putAll(this.subReports);
// Transform any collections etc into JRDataSources for sub reports.
if (this.subReportDataKeys != null) {
for (int i = 0; i < this.subReportDataKeys.length; i++) {
String key = this.subReportDataKeys[i];
model.put(key, convertReportData(model.get(key)));
}
}
}
populateHeaders(response);
renderReport(this.report, model, dataSource, response);
}
private void populateHeaders(HttpServletResponse response) {
// Apply the headers to the response.
for (Enumeration en = this.headers.propertyNames(); en.hasMoreElements();) {
String key = (String) en.nextElement();
response.addHeader(key, this.headers.getProperty(key));
}
}
/**
* Find an instance of <code>JRDataSource</code> in the given model map or create an
* appropriate JRDataSource for passed-in report data.
* <p>The default implementation checks for a model object under the
* specified "reportDataKey" first, then falls back to looking for a value
* of type <code>JRDataSource</code>, <code>java.util.Collection</code>,
* object array (in that order).
*
* @param model the model map, as passed in for view rendering
* @return the <code>JRDataSource</code>
* @throws IllegalArgumentException if no JRDataSource found
* @see #setReportDataKey
* @see #convertReportData
* @see #getReportDataTypes
*/
protected JRDataSource getReportData(Map model) throws IllegalArgumentException {
// Try model attribute with specified name.
if (this.reportDataKey != null) {
Object value = model.get(this.reportDataKey);
return convertReportData(value);
}
// Try to find matching attribute, of given prioritized types.
Object value = CollectionUtils.findValueOfType(model.values(), getReportDataTypes());
if (value != null) {
return convertReportData(value);
}
throw new IllegalArgumentException("No report data supplied in model " + model);
}
/**
* Convert the given report data value to a <code>JRDataSource</code>.
* <p>The default implementation delegates to <code>JasperReportUtils</code> unless
* the report data value is an instance of <code>JRDataSourceProvider</code>.
* A <code>JRDataSource</code>, <code>JRDataSourceProvider</code>,
* <code>java.util.Collection</code> or object array is detected.
* <code>JRDataSource</code>s are returned as is, whilst <code>JRDataSourceProvider</code>s
* are used to create an instance of <code>JRDataSource</code> which is then returned.
* The latter two are converted to <code>JRBeanCollectionDataSource</code> or
* <code>JRBeanArrayDataSource</code>, respectively.
*
* @param value the report data value to convert
* @return the JRDataSource
* @throws IllegalArgumentException if the value could not be converted
* @see org.springframework.ui.jasperreports.JasperReportsUtils#convertReportData
* @see net.sf.jasperreports.engine.JRDataSource
* @see net.sf.jasperreports.engine.JRDataSourceProvider
* @see net.sf.jasperreports.engine.data.JRBeanCollectionDataSource
* @see net.sf.jasperreports.engine.data.JRBeanArrayDataSource
*/
protected JRDataSource convertReportData(Object value) throws IllegalArgumentException {
if (value instanceof JRDataSourceProvider) {
try {
return ((JRDataSourceProvider) value).create(report);
}
catch (JRException ex) {
throw new IllegalArgumentException("Supplied JRDataSourceProvider is invalid: " + ex);
}
}
else {
return JasperReportsUtils.convertReportData(value);
}
}
/**
* Return the value types that can be converted to a <code>JRDataSource</code>,
* in prioritized order. Should only return types that the
* <code>convertReportData</code> method is actually able to convert.
* <p>Default value types are: <code>JRDataSource</code>,
* <code>JRDataSourceProvider</code> <code>java.util.Collection</code>
* and <code>Object</code> array.
*
* @return the value types in prioritized order
* @see #convertReportData
*/
protected Class[] getReportDataTypes() {
return new Class[]{JRDataSource.class, JRDataSourceProvider.class, Collection.class, Object[].class};
}
/**
* Allows sub-classes to get access to the <code>JasperReport</code> instance
* loaded by Spring.
*
* @return an instance of <code>JasperReport</code>.
*/
protected JasperReport getReport() {
return this.report;
}
/**
* Subclasses should implement this method to perform the actual rendering process.
*
* @param report the <code>JasperReport</code> to render
* @param parameters the map containing report parameters
* @param dataSource the <code>JRDataSource</code> containing the report data
* @param response the HTTP response the report should be rendered to
* @throws Exception if rendering failed
*/
protected abstract void renderReport(JasperReport report, Map parameters, JRDataSource dataSource, HttpServletResponse response)
throws Exception;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?