Un esempio di come generare un report di
SQL Server Reporting Services (SSRS) in
PDF usando
C# con
.NET Core.
Si parte aggiungendo un servizio
WCF in
Visual Studio
Aggiunta WCFche punta all'endpoint di
SSRS /reportserver/ReportExecution2005.asmx https://nomeServerReporting/reportserver/ReportExecution2005.asmx
Aggiunta la referenza (namespace WSReport) si può creare il metodo che restituisce il
client (ReportExecutionServiceSoapClient)
using System.Threading.Tasks;
using WSReport;
// default server
string REPORTING_URL = "https://nomeServerReporting";
private ReportExecutionServiceSoapClient CreateClient(string serverUrl = null)
{
if (serverUrl == null) {
serverUrl = REPORTING_URL;
}
var rsBinding = new BasicHttpBinding();
if (serverUrl.StartsWith("https:", StringComparison.InvariantCultureIgnoreCase))
{
rsBinding.Security.Mode = BasicHttpSecurityMode.Transport;
}
rsBinding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
// So we can download reports bigger than 64 KBytes
// See https://stackoverflow.com/questions/884235/wcf-how-to-increase-message-size-quota
rsBinding.MaxBufferPoolSize = 20000000;
rsBinding.MaxBufferSize = 20000000;
rsBinding.MaxReceivedMessageSize = 20000000;
// url del sirvizio di reporting
string url = serverUrl.TrimEnd('/') + "/ReportServer/ReportExecution2005.asmx";
var rsEndpointAddress = new EndpointAddress(url);
var rsClient = new ReportExecutionServiceSoapClient(rsBinding, rsEndpointAddress);
// imponsto l'autenticazione integrata con l'utente corrente
rsClient.ClientCredentials.Windows.AllowedImpersonationLevel = System.Security.Principal.TokenImpersonationLevel.Impersonation;
rsClient.ClientCredentials.Windows.ClientCredential = System.Net.CredentialCache.DefaultNetworkCredentials;
return rsClient;
}
e il metodo che genererà il report nel formato scelto
private async Task<FileBytes> GenerateReport(string reportPath, string reportFormat)
{
// creo il client usando la url del server di default
ReportExecutionServiceSoapClient rs = CreateClient();
var trustedHeader = new TrustedUserHeader();
// imposto il path e carico il report
LoadReportResponse loadReponse = await rs.LoadReportAsync(trustedHeader, reportPath, null);
// aggiungo i parametri (DateFrom e StatusIDs) al report
var reportParameters = new List<ParameterValue>();
reportParameters.Add(new ParameterValue() { Name = "DateFrom", Value = DateTime.Today.AddDays(-2).ToString("yyyy-MM-dd") });
reportParameters.Add(new ParameterValue() { Name = "StatusIDs", Value = "0,10,50,100" });
// imposto nel report i parametri e la lingua (it-IT)
await rs.SetExecutionParametersAsync(loadReponse.ExecutionHeader, trustedHeader, reportParameters.ToArray(), "it-IT");
// imposto le dimensioni del foglio per il render in PDF (foglio A4)
string width = "21cm";
string height = "29.7cm";
string deviceInfo = $"<DeviceInfo><PageHeight>{width}</PageHeight><PageWidth>{height}</PageWidth><PrintDpiX>300</PrintDpiX><PrintDpiY>300</PrintDpiY></DeviceInfo>";
var renderRequest = new RenderRequest(loadReponse.ExecutionHeader, trustedHeader, reportFormat, deviceInfo);
// mi faccio ritornare i bytes che rappresentano il report nel formato richiesto
RenderResponse response = await rs.RenderAsync(renderRequest);
// determino l'estensione in base al tipo di formato
string extension = "txt";
if (reportFormat.Equals("PDF"))
{
extension = "pdf";
}
else if (reportFormat.Equals("EXCELOPENXML"))
{
extension = "xlsx";
}
else if (reportFormat.Equals("WORDOPENXML"))
{
extension = "docx";
}
string fileName = $"AccountManagement_{DateTime.Today:yyyy-MM-dd}.{extension}";
return new FileBytes
{
FileName = fileName,
Content = response.Result
};
}
serve anche una piccola classe di supporto
FileBytespublic class FileBytes
{
public string FileName { get; set; }
public byte[] Content { get; set; }
}
A questo punto posso richiamare la generazione del report
// url completa del report http://nomeServerReporting/reports/report/Testing/Report1
string reportRelativeUrl = "/Testing/Report1";
string reportFormat = "PDF"; // oppure EXCELOPENXML o WORDOPENXML
// genero il report
var report = await GenearteReport(reportRelativeUrl , reportFormat);
// lo salvo
System.IO.File.WriteAllBytes($@"c:\tmp\{report.FileName}", report.Content);
Oltre al formato
PDF si può ottenere anche il formato
excel con la chiave
EXCELOPENXML.
Per un elenco completo dei comandi supportati vedi
URL access parameter referenceNel path del report
non includere la parte iniziale
/reports e sostituire eventuali escape dei caratteri come il
%20 con il corrispondente carattere
spazio (vedi
Url Encode e Decode).