Skip to main content
A newer version of this page is available. .
All docs
V21.2

How to Load a Report and Restore the Data Connection

  • 4 minutes to read

Prerequisites

Load Existing Reports

You can create and design a report in the Report Designer on any platform (WinForms, WPF, WebForms), or within the Visual Studio Report Designer, and save the report to the XML-based .repx file. For more information on report creation, refer to the following help topic: Get Started with DevExpress Reporting.

  1. The Report Viewer uses the report instance passed to the DxReportViewer.Report property to load a report. In this example, we use the OnInitialized application method for this purpose. A user passes a report name to the application, so we need a service that translates the report name to the report instance. The code of the page is as follows:

    @page "/viewer"
    @*A report name is passed in the URL Query string.*@
    @page "/viewer/{ReportName?}"
    
    @using DevExpress.Blazor.Reporting
    @using DevExpress.XtraReports.UI;
    
    <h3>Viewer</h3>
    
    <link rel="stylesheet" href="_content/DevExpress.Blazor/dx-blazor.css">
    <link rel="stylesheet" href="_content/DevExpress.Blazor.Reporting.Viewer/css/dx-blazor-reporting-components.css">
    
    <DxReportViewer @ref="reportViewer" Report="@Report">
    </DxReportViewer>
    
    @code {
        // The page uses a service that translates a report name to a report instance.
        [Inject] public DevExpress.XtraReports.Services.IReportProvider reportProvider { get; set; }
    
        DxReportViewer reportViewer { get; set; }
        XtraReport Report { get; set; }
        [Parameter] public string ReportName { get; set; }
    
        protected override void OnInitialized() {
            Report = reportProvider.GetReport(ReportName, null);
        }
    }
    
  2. A service that translates a report name to the report instance is an object with the IReportProvider service. To implement a service, create the ReportByNameService.cs file in the Services folder. The file has the following contents:

    using DevExpress.XtraReports.Services;
    using DevExpress.XtraReports.UI;
    using System;
    using System.IO;
    using System.Linq;
    
    public class ReportByNameService : IReportProvider {
        public XtraReport GetReport(string reportName, ReportProviderContext context) {
            string BaseDirectory = System.AppContext.BaseDirectory;
            XtraReport report = new XtraReport();
            var reportFolder = Path.Combine(BaseDirectory, "Reports");
    
            if (Directory.EnumerateFiles(reportFolder).
                Select(Path.GetFileNameWithoutExtension).Contains(reportName)) {
                byte[] reportBytes = File.ReadAllBytes(Path.Combine(reportFolder, reportName + ".repx"));
                using (MemoryStream ms = new MemoryStream(reportBytes))
                    report = XtraReport.FromXmlStream(ms);
            }
            return report;
        }
    }
    
  3. The service should be registered at application startup:

    using DevExpress.XtraReports.Services;
    
    public class Startup {
        // ...
        public void ConfigureServices(IServiceCollection services) {
            // ...
            services.AddScoped<IReportProvider, ReportByNameService>();
        }
    }
    

Get Connection String by Name

If the application is run at this point and the user specifies the report name in the query string, an error message is displayed that the report data source is unavailable. This happens because the report layout (.repx) file contains a connection string name, and the Report Viewer component attempts to use that name to create a connection string and retrieve data. The solution is to create a custom service that returns a connection by name.

To create a service that resolves a connection name to a valid connection, implement the IConnectionProviderFactory service that creates the IConnectionProviderService service. The IConnectionProviderService service retrieves a connection string from the application configuration file and returns the string to the Report Viewer.

In this example we use the SQLite nwind.db database that ships with the DevExpress installation. Copy the database to the DataSources folder and set the “Copy to output directory” property to Copy always.

Do the following:

  1. Install the SQLite NuGet package:

    dotnet add package System.Data.SQLite.Core --version 1.0.115.5
    
  2. Add a connection string to the appsettings.json file:

    "connectionStrings": {
        "DefaultConnection": "XpoProvider=SQLite;Data Source=DataSources/nwind.db"
    }
    
  3. Create the ReportDataConnectionService.cs file in the Services folder with the following code that implements the services:

    using DevExpress.DataAccess.Sql;
    using DevExpress.DataAccess.Web;
    using DevExpress.DataAccess.Wizard.Services;
    using Microsoft.Extensions.Configuration;
    
    public class ReportDataConnectionProviderFactory : IConnectionProviderFactory {
        private readonly IConfiguration _configuration;
        public ReportDataConnectionProviderFactory(IConfiguration configuration) {
            this._configuration = configuration;
        }
        public IConnectionProviderService Create() {
            return new ReportDataConnectionProviderService(_configuration);
        }
    }
    
    public class ReportDataConnectionProviderService : IConnectionProviderService {
        private readonly IConfiguration _configuration;
        public ReportDataConnectionProviderService(IConfiguration configuration) {
            this._configuration = configuration;
        }
        public SqlDataConnection LoadConnection(string connectionName) {
            string localConnectionName = "DefaultConnection";
            return new SqlDataConnection {
                Name = connectionName,
                ConnectionString = _configuration.GetConnectionString(localConnectionName)
            };
        }
    }
    

    The service returns the “DefaultConnection” connection string for any data connection to which a report is bound.

  4. Register the IConnectionProviderFactory and IConnectionProviderService services at application startup:

    using DevExpress.DataAccess.Web;
    using DevExpress.DataAccess.Wizard.Services;
    
        public class Startup {
            // ... 
            public void ConfigureServices(IServiceCollection services) {
                // ...
                services.AddScoped<IConnectionProviderFactory, ReportDataConnectionProviderFactory>();
                services.AddScoped<IConnectionProviderService, ReportDataConnectionProviderService>();
            }
        }
    

Run the Application

  1. Create a report that uses the Northwind database, or run the DevExpress demo and open the Report Designer for any report that uses Northwind data in our demo application, and save the report in XML format as a .repx file.
  2. Copy the report files (.repx) to the Reports folder in the application start directory.
  3. Run the project.
  4. When the browser opens the application, navigate to the viewer page and specify the report to open. If your project is based on the Microsoft Blazor template, the application appears as follows:

    DevExpress Report Viewer for Blazor displays a report