Reporting API with output name pattern not working

Hi:

I am using Mario David’s report scheduler and trying to email a report with an output name pattern. When I run the report from the GUI, the output file name is generated correctly. However, when I run his code, I find that the output name pattern is being used as the file name, rather than being translated by parameter substitution.

My pattern, if it matters, is:

mlgresponse_${Root.file}.xlsx

and my Root band is defined as:
image

I think I have located where the issue is. Mario calls the routine reportingApi.createAndSaveReport:

    private FileDescriptor generateReportFile(ScheduledReport scheduledReport, Report report, ReportTemplate reportTemplate) {
        FileDescriptor savedReport;
        savedReport = reportingApi.createAndSaveReport(
                report,
                reportTemplate,
                getReportParameters(scheduledReport),
                getFilename(scheduledReport, reportTemplate)
        );
        return savedReport;
    }

getFilename(…) is returning the template output file pattern (inside Mario’s code).

    private String getFilename(ScheduledReport scheduledReport, ReportTemplate reportTemplate) {
        ScheduledReportExtension extension = getExtension(scheduledReport);
        Optional<String> optionalFilename = extension.provideFilename(scheduledReport, reportTemplate);


        return optionalFilename
                .orElseGet(() -> defaultExtension().provideFilename(scheduledReport, reportTemplate)
                .orElse(null));
    }

When I look at that code, I see various versions, but at the bottom level, I see this:

    protected FileDescriptor createAndSaveReportDocument(Report report, ReportTemplate template, Map<String, Object> params, String fileName) {
        byte[] reportData = createReportDocument(report, template, params).getContent();
        String ext = template.getReportOutputType().toString().toLowerCase();

        return saveReport(reportData, fileName, ext);
    }

This receives a ReportOutputDocument back from createReportDocument, but it ignores the embedded documentName field and instead takes the value provided in the call. The embedded value has had parameter substitution done, but the template value has not.

How can we fix this? It looks like the issue is somewhere deep in reportingApi.createAndSaveReportDocument() and reportingApi.saveReport, which don’t check the ReportOutputDocument for a generated filename.

Hello @ericraskin,

Thanks for the detailed description of the problem. We created a ticket.

To solve this problem you need to override the method ReportingBean#createAndSaveReportDocument:

Create a bean CustomReportingBean.java in the core module:

public class CustomReportingBean extends ReportingBean {

    @Override
    protected FileDescriptor createAndSaveReportDocument(Report report, ReportTemplate template, Map<String, Object> params, String fileName) {
        ReportOutputDocument reportOutputDocument = createReportDocument(report, template, params);
        String fileNameResult = reportOutputDocument.getDocumentName();
        byte[] reportData = reportOutputDocument.getContent();
        String ext = template.getReportOutputType().toString().toLowerCase();

        return saveReport(reportData, fileNameResult, ext);
    }
}

Register the class in spring.xml of the project core module with the same identifier as the platform bean:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:context="http://www.springframework.org/schema/context">

    <!-- Annotation-based beans -->
    <context:component-scan base-package="com.company.report"/>

    <bean name="report_ReportingApi" class="com.company.report.CustomReportingBean"/>
</beans>

Documentation: Extending Business Logic

Regards,
Nikita

Thank you. I will try it.