diff --git a/.github/meta.yml b/.github/meta.yml new file mode 100644 index 0000000..13a190c --- /dev/null +++ b/.github/meta.yml @@ -0,0 +1,5 @@ +# GitHub Repository metadata +url: vcl-reports-non-interactive-export +website: https://docs.devexpress.com/VCL/405469/ExpressReports/vcl-reports +description: Generate DevExpress VCL Reports in backend and service applications. +tags: [vcl, pdf, reports, backend, service, cli, console] diff --git a/.gitignore b/.gitignore index 9db64f6..b6e1d5d 100644 --- a/.gitignore +++ b/.gitignore @@ -28,9 +28,10 @@ # Default Delphi compiler directories # Content of this directories are generated with each Compile/Construct of a project. -# Most of the time, files here have not there place in a code repository. -#Win32/ -#Win64/ +# Most of the time, files here have not their place in a code repository. +Win32/ +Win64/ +Win64x/ #OSX64/ #OSXARM64/ #Android/ @@ -61,6 +62,7 @@ *.cfg *.hpp *Resource.rc +*.rsp # Delphi local files (user-specific info) *.local @@ -75,8 +77,46 @@ __history/ __recovery/ *.~* + +# ------------------------------------------------------------ +# C++Builder specific +# ------------------------------------------------------------ + +# C++Builder compiler outputs +*.obj +*.hpp +*.ilc +*.ild +*.ilf +*.ils +*.map +*.tds + +# Precompiled headers +*.pch + +# C++Builder packages and libraries +*.bpl +*.bpi +*.lib +*.a +*.dll +*.so + +# C++Builder intermediate / cache files +*.cbproj.local +*.cbproj.identcache +*.cbproj.user +*.cbtemp + + # Castalia statistics file (since XE7 Castalia is distributed with Delphi) *.stat # Boss dependency manager vendor folder https://github.com/HashLoad/boss modules/ + +# Output files +*.pdf +*.docx +*.zip diff --git a/Delphi/Order.repx b/Delphi/Order.repx new file mode 100644 index 0000000..0a7aedd --- /dev/null +++ b/Delphi/Order.repx @@ -0,0 +1,159 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/Delphi/PDFReportGenerator.dpr b/Delphi/PDFReportGenerator.dpr new file mode 100644 index 0000000..eb81402 --- /dev/null +++ b/Delphi/PDFReportGenerator.dpr @@ -0,0 +1,76 @@ +program PDFReportGenerator; + +{$APPTYPE CONSOLE} + +{$R *.res} + +uses + System.SysUtils, System.Classes, System.StrUtils, dxBackend, dxBackend.Bundled, + dxBackend.ConnectionString.SQL, dxReport, dxReport.Parameters; +var + AOrderID: string; + +// Export a report to a PDF file in non-interactive mode: +// without showing the report in the Report Designer or Report Viewer, or otherwise using UI. +// Parameters: +// AOrderID: order ID to use in report data, for example, '11077' +procedure ExportReportToPdf(const AOrderID: string); +var + AConnection: TdxBackendDatabaseSQLConnection; + AReport: TdxReport; + AStream: TMemoryStream; + AOutputFileName: string; + +begin + // Step 1: Create a report instance and load the report layout + AReport := TdxReport.Create(nil); + try + // Set an internal report name (does not affect the exported PDF content and file name) + AReport.ReportName := 'OrderReport'; + // Load the report layout from the specified file + AReport.Layout.LoadFromFile('Order.repx'); + + // Step 2: Create a database connection + AConnection := TdxBackendDatabaseSQLConnection.Create(nil); + try + // Assign a database name matching the name specified in the report layout + AConnection.DisplayName := 'NWindConnectionString'; + // Assign a connection string required to use the local SQLite database + AConnection.ConnectionString := 'XpoProvider=SQLite; Data Source=nwind.db; Mode=ReadOnly'; + + // Step 3: Define Report Parameter Values + AReport.LoadParametersFromReport; + // Set the "OrderIdParameter" value in the report layout + AReport.Parameters['OrderIdParameter'].Value := AOrderID; + + // Step 4: Export a report to PDF + AStream := TMemoryStream.Create; + try + // Export a report to a memory stream in the PDF format + AReport.ExportToPDF(AStream); + // Save memory stream content to a file + AOutputFileName := 'Order_' + AOrderID + '.pdf'; + AStream.SaveToFile(AOutputFileName); + Writeln('Report saved to: ', AOutputFileName); + finally + AStream.Free; + end; + finally + AConnection.Free; + end; + finally + AReport.Free; + end; +end; + +// The helper application entry point that parses command-line parameters and calls the export procedure +begin + if ParamCount < 1 then + begin + Writeln('Error: OrderID parameter is required. For example: PDFReportGenerator.exe 11077'); + Halt(1); // Exit with error code 1 + end; + + AOrderID := ParamStr(1); // Read the first parameter as OrderID + ExportReportToPdf(AOrderID); +end. diff --git a/Delphi/PDFReportGenerator.dproj b/Delphi/PDFReportGenerator.dproj new file mode 100644 index 0000000..162d663 --- /dev/null +++ b/Delphi/PDFReportGenerator.dproj @@ -0,0 +1,1137 @@ + + + {115E31DF-EBF2-48A5-AFBC-BAB29ED4C364} + 20.3 + None + True + Release + Win32 + PDFReportGenerator + 3 + Console + PDFReportGenerator.dpr + + + true + + + true + Base + true + + + true + Base + true + + + true + Base + true + + + true + Cfg_1 + true + true + + + true + Cfg_1 + true + true + + + true + Base + true + + + .\$(Platform)\$(Config) + .\$(Platform)\$(Config) + false + false + false + false + false + System;Xml;Data;Datasnap;Web;Soap;$(DCC_Namespace) + PDFReportGenerator + 1033 + CompanyName=;FileDescription=$(MSBuildProjectName);FileVersion=1.0.0.0;InternalName=;LegalCopyright=;LegalTrademarks=;OriginalFilename=;ProgramID=com.embarcadero.$(MSBuildProjectName);ProductName=$(MSBuildProjectName);ProductVersion=1.0.0.0;Comments= + + + FireDACIBDriver;dxPScxCommonRS29;dxRibbonRS29;dxPSdxChartControlLnkRS29;vclwinx;DataSnapServer;dxPScxExtCommonRS29;dxRichEditControlCoreRS29;fmx;dxSpreadSheetReportDesignerRS29;vclie;DbxCommonDriver;bindengine;IndyIPCommon;VCLRESTComponents;DBXMSSQLDriver;FireDACCommonODBC;emsclient;dxComnRS29;dxFlowChartDesignerRS29;appanalytics;IndyProtocols;vclx;Skia.Package.RTL;dxBarExtDBItemsRS29;dbxcds;vcledge;cxVerticalGridRS29;FmxTeeUI;cxFireDACAdaptersRS29;dxPSDBTeeChartRS29;cxSchedulerWebServiceStorageRS29;DBXFirebirdDriver;dxRichEditControlRS29;dxPsPrVwAdvRS29;FireDACSqliteDriver;DbxClientDriver;dxPSdxGaugeControlLnkRS29;soapmidas;dxRibbonCustomizationFormRS29;TeeUI;dbexpress;dxEMFRS29;dxBackendRS29;dxDockingRS29;inet;vcltouch;dxPSdxFCLnkRS29;dxorgcRS29;FireDACDBXDriver;dxSpreadSheetCoreConditionalFormattingDialogsRS29;fmxdae;dxPSRichEditControlLnkRS29;dxPSdxSpreadSheetLnkRS29;CustomIPTransport;FireDACMSSQLDriver;cxADOAdaptersRS29;dxPSPrVwRibbonRS29;IndySystem;dxPScxTLLnkRS29;dxPSdxDBOCLnkRS29;dxGDIPlusRS29;ibxbindings;vclFireDAC;dxPSCoreRS29;dxSpreadSheetRS29;FireDACCommon;DataSnapServerMidas;FireDACODBCDriver;emsserverresource;cxGridEMFRS29;dxPSdxMapControlLnkRS29;dxGanttControlRS29;dxPScxVGridLnkRS29;dxPScxPivotGridLnkRS29;dxADOServerModeRS29;dxWizardControlRS29;bindcompdbx;rtl;FireDACMySQLDriver;dxCloudServiceLibraryRS29;cxIBXAdaptersRS29;dxServerModeRS29;DBXSqliteDriver;dxBarDBNavRS29;DBXSybaseASEDriver;dxSpreadSheetCoreRS29;dxNavBarRS29;vclimg;DataSnapFireDAC;inetdbxpress;FireDAC;xmlrtl;ibxpress;dxFireDACEMFRS29;dsnap;FireDACDb2Driver;dxPSdxLCLnkRS29;DBXOracleDriver;DBXInformixDriver;vclib;fmxobj;bindcompvclsmp;DataSnapNativeClient;DatasnapConnectorsFreePascal;dxPSLnksRS29;dxmdsRS29;dxPSdxOCLnkRS29;cxSchedulerGridRS29;dxPScxSchedulerLnkRS29;emshosting;dxADOEMFRS29;dxChartControlRS29;dxPSdxDBTVLnkRS29;FireDACCommonDriver;dxGaugeControlRS29;IndyIPClient;dxPDFViewerRS29;bindcompvclwinx;dxOrgChartAdvancedCustomizeFormRS29;emsedge;bindcompfmx;dxBarExtItemsRS29;dxReportsRS29;dxFlowChartLayoutsRS29;inetdb;dxdborRS29;ibmonitor;FireDACASADriver;Tee;dxPScxGridLnkRS29;cxPivotGridChartRS29;vclactnband;fmxFireDAC;FireDACInfxDriver;dxRichEditCoreRS29;cxTreeListdxBarPopupMenuRS29;DBXMySQLDriver;dxFlowChartAdvancedCustomizeFormRS29;VclSmp;cxSchedulerRibbonStyleEventEditorRS29;DataSnapCommon;dxPSTeeChartRS29;fmxase;dxtrmdRS29;dxFlowChartRS29;DBXOdbcDriver;dbrtl;dxPScxPCProdRS29;FireDACOracleDriver;Skia.Package.FMX;TeeDB;FireDACMSAccDriver;cxGridRS29;dxSpellCheckerRS29;DataSnapIndy10ServerTransport;dxRichEditDocumentModelRS29;dxMapControlRS29;DataSnapConnectors;vcldsnap;DBXInterBaseDriver;FireDACMongoDBDriver;FireDACTDataDriver;cxLibraryRS29;Skia.Package.VCL;vcldb;dxPSdxPDFViewerLnkRS29;cxSchedulerTreeBrowserRS29;bindcomp;dxTabbedMDIRS29;cxExportRS29;inetstn;IndyCore;RESTBackendComponents;dxHttpIndyRequestRS29;dxTileControlRS29;dxFireDACServerModeRS29;cxPivotGridOLAPRS29;FireDACADSDriver;RaizeComponentsVclDb;dxDashboardsRS29;RESTComponents;IndyIPServer;vcl;dsnapxml;adortl;dsnapcon;DataSnapClient;DataSnapProviderClient;dxCoreRS29;cxPivotGridRS29;dxdbtrRS29;DBXDb2Driver;dxSkinsCoreRS29;emsclientfiredac;FireDACPgDriver;FireDACDSDriver;dxBarRS29;tethering;bindcompvcl;CloudService;DBXSybaseASADriver;dxSpreadSheetConditionalFormattingDialogsRS29;cxTreeListRS29;FMXTee;soaprtl;dxDBXServerModeRS29;cxSchedulerRS29;RaizeComponentsVcl;soapserver;$(DCC_UsePackage) + Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;Bde;$(DCC_Namespace) + Debug + true + $(BDS)\bin\Artwork\Windows\UWP\delphi_UwpDefault_44.png + $(BDS)\bin\Artwork\Windows\UWP\delphi_UwpDefault_150.png + 11032 + (None) + none + .\ + + + FireDACIBDriver;dxPScxCommonRS29;dxRibbonRS29;dxPSdxChartControlLnkRS29;vclwinx;DataSnapServer;dxPScxExtCommonRS29;dxRichEditControlCoreRS29;fmx;dxSpreadSheetReportDesignerRS29;vclie;DbxCommonDriver;bindengine;IndyIPCommon;VCLRESTComponents;DBXMSSQLDriver;FireDACCommonODBC;emsclient;dxComnRS29;dxFlowChartDesignerRS29;appanalytics;IndyProtocols;vclx;dxBarExtDBItemsRS29;dbxcds;vcledge;cxVerticalGridRS29;FmxTeeUI;cxFireDACAdaptersRS29;dxPSDBTeeChartRS29;cxSchedulerWebServiceStorageRS29;DBXFirebirdDriver;dxRichEditControlRS29;dxPsPrVwAdvRS29;FireDACSqliteDriver;DbxClientDriver;dxPSdxGaugeControlLnkRS29;soapmidas;dxRibbonCustomizationFormRS29;TeeUI;dbexpress;dxEMFRS29;dxBackendRS29;dxDockingRS29;inet;vcltouch;dxPSdxFCLnkRS29;dxorgcRS29;FireDACDBXDriver;dxSpreadSheetCoreConditionalFormattingDialogsRS29;fmxdae;dxPSRichEditControlLnkRS29;dxPSdxSpreadSheetLnkRS29;CustomIPTransport;FireDACMSSQLDriver;cxADOAdaptersRS29;dxPSPrVwRibbonRS29;IndySystem;dxPScxTLLnkRS29;dxPSdxDBOCLnkRS29;dxGDIPlusRS29;ibxbindings;vclFireDAC;dxPSCoreRS29;dxSpreadSheetRS29;FireDACCommon;DataSnapServerMidas;FireDACODBCDriver;emsserverresource;cxGridEMFRS29;dxPSdxMapControlLnkRS29;dxGanttControlRS29;dxPScxVGridLnkRS29;dxPScxPivotGridLnkRS29;dxADOServerModeRS29;dxWizardControlRS29;bindcompdbx;rtl;FireDACMySQLDriver;dxCloudServiceLibraryRS29;cxIBXAdaptersRS29;dxServerModeRS29;DBXSqliteDriver;dxBarDBNavRS29;DBXSybaseASEDriver;dxSpreadSheetCoreRS29;dxNavBarRS29;vclimg;DataSnapFireDAC;inetdbxpress;FireDAC;xmlrtl;ibxpress;dxFireDACEMFRS29;dsnap;FireDACDb2Driver;dxPSdxLCLnkRS29;DBXOracleDriver;DBXInformixDriver;vclib;fmxobj;bindcompvclsmp;DataSnapNativeClient;DatasnapConnectorsFreePascal;dxPSLnksRS29;dxmdsRS29;dxPSdxOCLnkRS29;cxSchedulerGridRS29;dxPScxSchedulerLnkRS29;emshosting;dxADOEMFRS29;dxChartControlRS29;dxPSdxDBTVLnkRS29;FireDACCommonDriver;dxGaugeControlRS29;IndyIPClient;dxPDFViewerRS29;bindcompvclwinx;dxOrgChartAdvancedCustomizeFormRS29;emsedge;bindcompfmx;dxBarExtItemsRS29;dxReportsRS29;dxFlowChartLayoutsRS29;inetdb;dxdborRS29;ibmonitor;FireDACASADriver;Tee;dxPScxGridLnkRS29;cxPivotGridChartRS29;vclactnband;fmxFireDAC;FireDACInfxDriver;dxRichEditCoreRS29;cxTreeListdxBarPopupMenuRS29;DBXMySQLDriver;dxFlowChartAdvancedCustomizeFormRS29;VclSmp;cxSchedulerRibbonStyleEventEditorRS29;DataSnapCommon;dxPSTeeChartRS29;fmxase;dxtrmdRS29;dxFlowChartRS29;DBXOdbcDriver;dbrtl;dxPScxPCProdRS29;FireDACOracleDriver;TeeDB;FireDACMSAccDriver;cxGridRS29;dxSpellCheckerRS29;DataSnapIndy10ServerTransport;dxRichEditDocumentModelRS29;dxMapControlRS29;DataSnapConnectors;vcldsnap;DBXInterBaseDriver;FireDACMongoDBDriver;FireDACTDataDriver;cxLibraryRS29;Skia.Package.VCL;vcldb;dxPSdxPDFViewerLnkRS29;cxSchedulerTreeBrowserRS29;bindcomp;dxTabbedMDIRS29;cxExportRS29;inetstn;IndyCore;RESTBackendComponents;dxHttpIndyRequestRS29;dxTileControlRS29;dxFireDACServerModeRS29;cxPivotGridOLAPRS29;FireDACADSDriver;RaizeComponentsVclDb;dxDashboardsRS29;RESTComponents;IndyIPServer;vcl;dsnapxml;adortl;dsnapcon;DataSnapClient;DataSnapProviderClient;dxCoreRS29;cxPivotGridRS29;dxdbtrRS29;DBXDb2Driver;dxSkinsCoreRS29;emsclientfiredac;FireDACPgDriver;FireDACDSDriver;dxBarRS29;tethering;bindcompvcl;CloudService;DBXSybaseASADriver;dxSpreadSheetConditionalFormattingDialogsRS29;cxTreeListRS29;FMXTee;soaprtl;dxDBXServerModeRS29;cxSchedulerRS29;RaizeComponentsVcl;soapserver;$(DCC_UsePackage) + true + $(BDS)\bin\Artwork\Windows\UWP\delphi_UwpDefault_44.png + $(BDS)\bin\Artwork\Windows\UWP\delphi_UwpDefault_150.png + Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;$(DCC_Namespace) + Debug + (None) + 11064 + none + PDFReportGenerator_Icon.ico + .\ + + + DEBUG;$(DCC_Define) + true + false + true + true + true + true + true + + + false + 1033 + + + 1033 + + + false + RELEASE;$(DCC_Define) + 0 + 0 + 1033 + + + + MainSource + + + Base + + + Cfg_1 + Base + + + Cfg_2 + Base + + + + Delphi.Personality.12 + Application + + + + PDFReportGenerator.dpr + + + Embarcadero C++Builder Office 2000 Servers Package + Embarcadero C++Builder Office XP Servers Package + Microsoft Office 2000 Sample Automation Server Wrapper Components + Microsoft Office XP Sample Automation Server Wrapper Components + + + + + + true + + + + + true + + + + + true + + + + + PDFReportGenerator.exe + true + + + + + PDFReportGenerator.exe + true + + + + + PDFReportGenerator.rsm + true + + + + + 1 + + + Contents\MacOS + 1 + + + 0 + + + + + res\xml + 1 + + + res\xml + 1 + + + + + library\lib\armeabi + 1 + + + library\lib\armeabi + 1 + + + + + library\lib\armeabi-v7a + 1 + + + + + library\lib\mips + 1 + + + library\lib\mips + 1 + + + + + library\lib\armeabi-v7a + 1 + + + library\lib\arm64-v8a + 1 + + + + + library\lib\armeabi-v7a + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable-anydpi-v21 + 1 + + + res\drawable-anydpi-v21 + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + res\values-v21 + 1 + + + res\values-v21 + 1 + + + + + res\values-v31 + 1 + + + res\values-v31 + 1 + + + + + res\values-v35 + 1 + + + res\values-v35 + 1 + + + + + res\drawable-anydpi-v26 + 1 + + + res\drawable-anydpi-v26 + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable-anydpi-v33 + 1 + + + res\drawable-anydpi-v33 + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + res\values-night-v21 + 1 + + + res\values-night-v21 + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable-xxhdpi + 1 + + + res\drawable-xxhdpi + 1 + + + + + res\drawable-xxxhdpi + 1 + + + res\drawable-xxxhdpi + 1 + + + + + res\drawable-ldpi + 1 + + + res\drawable-ldpi + 1 + + + + + res\drawable-mdpi + 1 + + + res\drawable-mdpi + 1 + + + + + res\drawable-hdpi + 1 + + + res\drawable-hdpi + 1 + + + + + res\drawable-xhdpi + 1 + + + res\drawable-xhdpi + 1 + + + + + res\drawable-mdpi + 1 + + + res\drawable-mdpi + 1 + + + + + res\drawable-hdpi + 1 + + + res\drawable-hdpi + 1 + + + + + res\drawable-xhdpi + 1 + + + res\drawable-xhdpi + 1 + + + + + res\drawable-xxhdpi + 1 + + + res\drawable-xxhdpi + 1 + + + + + res\drawable-xxxhdpi + 1 + + + res\drawable-xxxhdpi + 1 + + + + + res\drawable-small + 1 + + + res\drawable-small + 1 + + + + + res\drawable-normal + 1 + + + res\drawable-normal + 1 + + + + + res\drawable-large + 1 + + + res\drawable-large + 1 + + + + + res\drawable-xlarge + 1 + + + res\drawable-xlarge + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + res\drawable-anydpi-v24 + 1 + + + res\drawable-anydpi-v24 + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable-night-anydpi-v21 + 1 + + + res\drawable-night-anydpi-v21 + 1 + + + + + res\drawable-anydpi-v31 + 1 + + + res\drawable-anydpi-v31 + 1 + + + + + res\drawable-night-anydpi-v31 + 1 + + + res\drawable-night-anydpi-v31 + 1 + + + + + 1 + + + Contents\MacOS + 1 + + + 0 + + + + + Contents\MacOS + 1 + .framework + + + Contents\MacOS + 1 + .framework + + + Contents\MacOS + 1 + .framework + + + 0 + + + + + 1 + .dylib + + + 1 + .dylib + + + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + 0 + .dll;.bpl + + + + + 1 + .dylib + + + 1 + .dylib + + + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + Contents\MacOS + 1 + .dylib + + + 0 + .bpl + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + Contents\Resources\StartUp\ + 0 + + + Contents\Resources\StartUp\ + 0 + + + Contents\Resources\StartUp\ + 0 + + + 0 + + + + + 1 + + + 1 + + + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + + + ..\ + 1 + + + ..\ + 1 + + + ..\ + 1 + + + + + Contents + 1 + + + Contents + 1 + + + Contents + 1 + + + + + Contents\Resources + 1 + + + Contents\Resources + 1 + + + Contents\Resources + 1 + + + + + library\lib\armeabi-v7a + 1 + + + library\lib\arm64-v8a + 1 + + + 1 + + + 1 + + + 1 + + + 1 + + + Contents\MacOS + 1 + + + Contents\MacOS + 1 + + + Contents\MacOS + 1 + + + 0 + + + + + library\lib\armeabi-v7a + 1 + + + + + 1 + + + 1 + + + 1 + + + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + + + ..\ + 1 + + + ..\ + 1 + + + ..\ + 1 + + + + + 1 + + + 1 + + + 1 + + + + + ..\$(PROJECTNAME).launchscreen + 64 + + + ..\$(PROJECTNAME).launchscreen + 64 + + + + + 1 + + + 1 + + + 1 + + + + + Assets + 1 + + + Assets + 1 + + + + + Assets + 1 + + + Assets + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + + + + + + + + + + + + + True + True + + + 12 + + + + + diff --git a/Delphi/PDFReportGenerator.res b/Delphi/PDFReportGenerator.res new file mode 100644 index 0000000..cf4b026 Binary files /dev/null and b/Delphi/PDFReportGenerator.res differ diff --git a/Delphi/PDFReportGenerator_Icon.ico b/Delphi/PDFReportGenerator_Icon.ico new file mode 100644 index 0000000..60cda0a Binary files /dev/null and b/Delphi/PDFReportGenerator_Icon.ico differ diff --git a/Delphi/nwind.db b/Delphi/nwind.db new file mode 100644 index 0000000..b96cf97 Binary files /dev/null and b/Delphi/nwind.db differ diff --git a/README.md b/README.md index 6ad99eb..8682ef8 100644 --- a/README.md +++ b/README.md @@ -4,12 +4,191 @@ [![](https://img.shields.io/badge/💬_Leave_Feedback-feecdd?style=flat-square)](#does-this-example-address-your-development-requirementsobjectives) +# DevExpress VCL Reports — Generate Reports in a Backend / Service Application + +This example uses DevExpress Reports for Delphi/C++Builder to generate reports in a command line application. +The application accepts an order ID parameter, queries the database for order data, +and exports an "order" report as a PDF file. + +This example bypasses the DevExpress Report Viewer dialog and generates a report +using the DevExpress Reports backend. +Use the approach demonstrated in this sample project to implement +Web API backends, Windows Services, workflows, and scheduled jobs. +This approach can be particularly beneficial for the following usage scenarios +(reports generated without direct user interaction): + +- Mass-export reports to PDF, DOCX, image, and other formats. +- Share, email, and print report documents silently. +- Implement custom report management UIs. + +--- + +![A PDF report example generated by a command line application (demonstrates order number 11077)](./images/report.png) + +--- + +## Prerequisites + +[DevExpress Reports Prerequisites][req] + +[req]: https://docs.devexpress.com/VCL/405773/ExpressCrossPlatformLibrary/vcl-backend/reports-dashboards-app-deployment#vcl-reportsdashboards-prerequisites + +## Test the Example + +1. Open and build the Delphi project in the RAD Studio. +2. Start a console session and navigate to the _Delphi_ project directory. +3. Run the app and specify the order ID (a number between 10248 and 11077): + + ```console + > PDFReportGenerator.exe 11077 + + Report saved to: ..\Order_11077.pdf + ``` +4. Generate reports for other order IDs and compare generated PDF files. + +## Implementation Details + +Follow the steps below to create an application that imports a report layout from a file, +binds the layout to data, and exports the generated report to a PDF file. + + +### Step 1: Initialize a Report and Import a Report Layout + +An application requires a template report layout previously created in the [Report Designer][designer]. +You can [import a report layout from a REPX file][file] or [load a layout from a database][database]. + +[designer]: https://docs.devexpress.com/VCL/405469/ExpressReports/vcl-reports +[file]: https://github.com/DevExpress-Examples/vcl-reports-store-layout-template-file +[database]: https://github.com/DevExpress-Examples/vcl-reports-store-layout-template-database + +This example imports a report layout from the `Order.repx` file. + +**Delphi:** +```pas +AReport := TdxReport.Create(nil); // AReport: TdxReport; +try + // Set an internal report name (does not affect the exported content) + AReport.ReportName := 'Order Report'; + // Load the report layout from the specified file + AReport.Layout.LoadFromFile('Order.repx'); + // ... +finally + AReport.Free; +end; +``` + + +### Step 2: Create a Database Connection + +Create a database connection component to supply data to the report. +This example uses a SQL connection component with a built-in SQLite engine to load the Northwind sample database stored in `nwind.db`. + +```pas +// AConnection: TdxBackendDatabaseSQLConnection; +AConnection := TdxBackendDatabaseSQLConnection.Create(nil); +try + // Assign a database name matching the name specified in the report layout + AConnection.DisplayName := 'NWindConnectionString'; + // Assign a connection string required to use the local SQLite database + AConnection.ConnectionString := 'XpoProvider=SQLite; Data Source=nwind.db; Mode=ReadOnly'; + // ... +finally + AConnection.Free; +end; +``` + +For detailed information on data source management and supported database engines, refer to the following help topic: +[VCL Backend: Supported Database Systems][dbms]. + +[dbms]: https://docs.devexpress.com/VCL/405703/ExpressCrossPlatformLibrary/vcl-backend/vcl-backend-supported-database-systems + +### Step 3: Define Report Parameter Values + +A report layout may include one or more parameters. +Parameters allow you to modify database queries and generate different reports +based on the same report template and underlying data. +For example, `Order.repx` includes a single `OrderIDParameter` that filters data by order ID. + +To modify parameters, load them using the `LoadParametersFromReport` method +and assign values to `Report.Parameters` list members as follows: + +**Delphi:** +```pas +AReport.LoadParametersFromReport; +// Set the "OrderIdParameter" value in the report layout +AReport.Parameters['OrderIdParameter'].Value := AOrderID; +``` + + +### Step 4: Export Report Content to a File + +This example exports a report to a PDF file: + +**Delphi:** +```pas +AStream := TMemoryStream.Create; // AStream: TMemoryStream; +try + // Export a report to a memory stream in the PDF format + AReport.ExportToPDF(AStream); + // Save memory stream content to a file + AStream.SaveToFile('Order_' + AOrderID + '.pdf'); +finally + AStream.Free; +end; +``` + +### Export Multiple Reports + +The approach outlined in this example allows you to generate and export multiple reports based on the same layout and data +using a list of parameters. +You need to initialize the report layout and data connection once (steps 1 and 2) +and repeat steps 3 and 4 for each parameter. + +**Delphi:** + +```pas +// ... +AReport.LoadParametersFromReport; + +for AOrderID in AOrderIDList: + AReport.Parameters['OrderIdParameter'].Value := AOrderID; + + AStream := TMemoryStream.Create; // AStream: TMemoryStream; + try + // Export a report to a memory stream in the PDF format + AReport.ExportToPDF(AStream); + // Save memory stream content to a file + AStream.SaveToFile('Order_' + AOrderID + '.pdf'); + finally + AStream.Free; + end; +end; +``` + + +## Files to Review + +- [`Delphi/PDFReportGenerator.dpr`](./Delphi/PDFReportGenerator.dpr) generates a report in non-interactive (headless) mode. +- [`Order.repx`](./Order.repx) contains a report layout designed to generate a customer order report. + You can view and edit this file using the [file storage example application](https://github.com/DevExpress-Examples/vcl-reports-store-layout-template-file). +- [`nwind.db`](./nwind.db) contains the Northwind sample database. + + +## Documentation and Examples + +- [Introduction to VCL Reports](https://docs.devexpress.com/VCL/405469/ExpressReports/vcl-reports) +- [Tutorial: Create a table report using the Report Wizard](https://docs.devexpress.com/VCL/405760/ExpressReports/getting-started/create-table-report-using-report-wizard) +- [How to store report layouts in REPX files (example application)](https://github.com/DevExpress-Examples/vcl-reports-store-layout-template-file) +- [How to store report layouts in a database (example application)](https://github.com/DevExpress-Examples/vcl-reports-store-layout-template-database) +- [How to use SQLite as a data source for reports (as demonstrated in the current example)](https://docs.devexpress.com/VCL/405750/ExpressCrossPlatformLibrary/vcl-backend/database-engines/vcl-backend-sqlite-support) +- [API reference: `TdxReport.Layout` Property](https://docs.devexpress.com/VCL/dxReport.TdxReport.Layout) +- [API reference: `TdxBackendDatabaseSQLConnection` Component](https://docs.devexpress.com/VCL/dxBackend.ConnectionString.SQL.TdxBackendDatabaseSQLConnection) + - -## Does this example address your development requirements/objectives? +## Does This Example Address Your Development Requirements/Objectives? -[](https://www.devexpress.com/support/examples/survey.xml?utm_source=github&utm_campaign=vcl-reports-filter-export-report-pdf-in-console-app&~~~was_helpful=yes) [](https://www.devexpress.com/support/examples/survey.xml?utm_source=github&utm_campaign=vcl-reports-filter-export-report-pdf-in-console-app&~~~was_helpful=no) +[](https://www.devexpress.com/support/examples/survey.xml?utm_source=github&utm_campaign=vcl-reports-non-interactive-export&~~~was_helpful=yes) [](https://www.devexpress.com/support/examples/survey.xml?utm_source=github&utm_campaign=vcl-reports-non-interactive-export&~~~was_helpful=no) (you will be redirected to DevExpress.com to submit your response) diff --git a/images/report.png b/images/report.png new file mode 100644 index 0000000..821b6db Binary files /dev/null and b/images/report.png differ