Quartz.net windows service does not execute job which referencesSSRS web service - reporting-services

I have used two web references of ssrs reporting execution service to generate the report. I am using quartz.net windows service for scheduling ssrs reports. My Windows service is working when I use the StdSchedulerFactory.GetDefaultScheduler() but as I execute my job in a Quartz service remotely and use GetScheduler() , it's not working.
public void Execute(IJobExecutionContext context)
{
RS2005.ReportingService2005 rs;
RE2005.ReportExecutionService rsExec;
// Create a new proxy to the web service
rs = new RS2005.ReportingService2005();
rsExec = new RE2005.ReportExecutionService();
// Authenticate to the Web service using Windows credentials
rs.Credentials = System.Net.CredentialCache.DefaultCredentials;
rsExec.Credentials = System.Net.CredentialCache.DefaultCredentials;
rs.Url = "http://127.0.0.1:7001/ReportServer/reportservice2005.asmx";
rsExec.Url = "http://127.0.0.1:7001/ReportServer/reportexecution2005.asmx";
string historyID = null;
string deviceInfo = null;
string format = "PDF";
Byte[] results;
string encoding = String.Empty;
string mimeType = String.Empty;
string extension = String.Empty;
RE2005.Warning[] warnings = null;
string[] streamIDs = null;
// Path of the Report - XLS, PDF etc.
string fileName = "samplereport.pdf";
// Name of the report - Please note this is not the RDL file.
string _reportName = #"/reports_Debug/reportname";
string _historyID = null;
bool _forRendering = false;
RS2005.ParameterValue[] _values = null;
RS2005.DataSourceCredentials[] _credentials = null;
RS2005.ReportParameter[] _parameters = null;
try
{
_parameters = rs.GetReportParameters(_reportName, _historyID, _forRendering, _values, _credentials);
RE2005.ExecutionInfo ei = rsExec.LoadReport(_reportName, historyID);
RE2005.ParameterValue[] parameters = new RE2005.ParameterValue[8];
if (_parameters.Length > 0)
{
parameters[0] = new RE2005.ParameterValue();
parameters[0].Name = "FromDate";
parameters[0].Value = "1/1/2016";
parameters[1] = new RE2005.ParameterValue();
parameters[1].Name = "ToDate";
parameters[1].Value = "1/21/2016"; // June
}
rsExec.SetExecutionParameters(parameters, "en-us");
results = rsExec.Render(format, deviceInfo,
out extension, out encoding,
out mimeType, out warnings, out streamIDs);
using (FileStream stream = File.OpenWrite(fileName))
{
stream.Write(results, 0, results.Length);
}
}
catch (Exception ex)
{
throw ex;
}
}

Related

SSRS Report Execution Service: export to xlsx without error

Hello thanks for looking.
I have some .net code that uses the SSRS Report Execution Service to download a report for the user as an xlsx file.
It works & everything in the report is present & accounted for.
One annoying thing though. When opened in Excel 365 it gives a popup saying:
We found a problem with some content in "theReport.xlsx" Do you want us to try to recover as much as we can? If you trust the source of this workbook click yes
When I click yes then it indicates that the workbook was repaired and the report looks normal.
It does not give any indication what it repaired in the log file, just that it was repaired.
Please take a look at my code. Perhaps there is something small I can change to get rid of the error when the Excel sheet is opened.
private void DownloadQuoteExport()
{
string reportName = "reportName";
string fileName = "filename";
//create web services instance
ReportExecutionService rs = getService();
//render report 1st parameter
ParameterValue param1 = new ParameterValue();
param1.Name = "QuoteID";
param1.Value = quoteId.ToString();
try
{
executeReport(reportName, new ParameterValue[] { param1 }, "EXCELOPENXML", fileName, rs);
}
catch (Exception ex)
{
Response.Write(ex.Message + "<br>" + ex.StackTrace.ToString());
}
}
private void executeReport(String reportName, ParameterValue[] rptParams, String rptFormat, string strRptFileName, ReportExecutionService service)
{
string encoding;
string mimeType;
string extension;
Warning[] warnings = null;
string[] streamIDs = null;
string historyID = null;
ExecutionInfo execInfo = new ExecutionInfo();
ExecutionHeader execHeader = new ExecutionHeader();
service.ExecutionHeaderValue = execHeader;
execInfo = service.LoadReport(reportName, historyID);
service.SetExecutionParameters(rptParams, "en-us");
String SessionId = service.ExecutionHeaderValue.ExecutionID;
byte[] result = service.Render(rptFormat, null, out extension, out encoding, out mimeType, out warnings, out streamIDs);
Response.ClearContent();
if (rptFormat == "EXCELOPENXML")
{
Response.AppendHeader("content-disposition", "attachment; filename=" + strRptFileName + ".xlsx");
Response.ContentType = "application/application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
}
Response.BinaryWrite(result);
Response.Flush();
}
This is finally what worked.
private void executeReport(String reportName, ParameterValue[] rptParams, String rptFormat, string strRptFileName, ReportExecutionService service)
{
string encoding;
string mimeType;
string extension;
Warning[] warnings = null;
string[] streamIDs = null;
string historyID = null;
ExecutionInfo execInfo = new ExecutionInfo();
ExecutionHeader execHeader = new ExecutionHeader();
service.ExecutionHeaderValue = execHeader;
execInfo = service.LoadReport(reportName, historyID);
service.SetExecutionParameters(rptParams, "en-us");
String SessionId = service.ExecutionHeaderValue.ExecutionID;
byte[] result = service.Render(rptFormat, null, out extension, out encoding, out mimeType, out warnings, out streamIDs);
Response.ClearContent();
Response.Clear();
if (rptFormat == "EXCELOPENXML")
{
Response.AppendHeader("content-disposition", "attachment; filename=" + strRptFileName + ".xlsx");
Response.ContentType = "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
}
Response.BinaryWrite(result);
Response.Flush();
Response.SuppressContent = true;
try
{
HttpContext.Current.ApplicationInstance.CompleteRequest();
}
catch (ThreadAbortException ex)
{
//ignore
}
}

SSRS -Image not rendering on HTML 4.0 Report(Unauthorization )

I am working on SSRS report. I am accessing report using web services (using web refrences)
I am using ReportExecutionService class to render report in the html 4.0 format and finaly I attach rendered HTML to my page DIV. Report is rendering very fine in HTML format but the images on that is not rendering properly because of missing authentication for images
for that I just replace the src attribute of the img tag in the response returned from the SSRS report execution service with the url to this location below is code for render report:-
public string Render(string reportDirectory,string reportName,string reportFormat, ParameterValue[]parameters )
{
_reportServerExecutionService.ExecutionHeaderValue = new ExecutionHeader();
_reportServerExecutionService.TrustedUserHeaderValue = new TrustedUserHeader();
_reportServerExecutionService.LoadReport("/GES-MVC/GES_FWCR",null);
_reportServerExecutionService.SetExecutionParameters(parameters, "en-us");
string encoding;
string mimeType;
string extension;
Warning[] warnings;
string[] streamIds;
var result = _reportServerExecutionService.Render(reportFormat, #"<DeviceInfo><Toolbar>False</Toolbar></DeviceInfo>", out extension, out encoding, out mimeType, out warnings, out streamIds);
//Here is logic for image replcaement
string html = string.Empty;
html = System.Text.Encoding.Default.GetString(result);
html = GetReportImages(_reportServerExecutionService, _reportServerExecutionService.ExecutionHeaderValue, _reportServerExecutionService.TrustedUserHeaderValue, reportFormat, streamIds, html);
return html;
}
and function (code) for image replacement
public string GetReportImages(ReportExecutionService _reportServerExecutionService, ExecutionHeader executionHeaderValue, TrustedUserHeader trustedUserHeaderValue, string reportFormat, string[] streamIds, string html)
{
if (reportFormat.Equals("HTML4.0") && streamIds.Length > 0)
{
string devInfo;
string mimeType;
string Encoding;
string fileExtension = ".jpg";
string SessionId;
Byte[] image;
foreach (string streamId in streamIds)
{
SessionId = Guid.NewGuid().ToString().Replace("}", "").Replace("{", "").Replace("-", "");
string reportreplacementname = string.Concat(streamId, "_", SessionId, fileExtension);
html = html.Replace(streamId, string.Concat(#"Report\GraphFiles\", reportreplacementname));
devInfo = "";
image= _reportServerExecutionService.RenderStream(reportFormat, streamId, devInfo, out Encoding, out mimeType);
System.IO.FileStream stream = System.IO.File.OpenWrite(HttpContext.Current.Request.PhysicalApplicationPath + "Report\\GraphFiles\\" + reportreplacementname);
stream.Write(image, 0, image.Length);
stream.Close();
mimeType = "text/html";
}
}
return html;
}
but issue is that image is saved into folder and also src tag is replaced into html ,still image is not display on report Can anybody have solution for this or any related code for same
Thanks In Advance
This is close to being correct. There is one small part you are missing.
Not only do you have to intercept the streams and save each to a temp location that is accessible to your app, you also have to let SSRS know that the renderer should source the dynamic images to your new location.
The way to let the renderer know about the new location is to override the DeviceInfo.StreamRoot passed into the Render() method.
string thisReportInstanceID = Guid.NewGuid();
string thisReportInstanceTempFolder = Path.Combine("Temp",thisReportInstanceID );
string physicalTempFolder = Path.Combine(<YourPhysicalWebRoot>,thisReportInstanceTempFolder );
string virtualTempFolder =<YourVirtualWebRoot>+"/Temp/"+thisReportInstanceID );
Directory.Create(physicalTempFolder );
StringBuilder devInfo = new StringBuilder();
if (format.ToUpper().StartsWith("HTML"))
{
devInfo.Append("<DeviceInfo>");
//StreamRoot should be your fully qualified domain name + temp folder for this report instance.
devInfo.Append("<StreamRoot>" + virtualTempFolder+ "</StreamRoot>");
devInfo.Append("</DeviceInfo>");
}
var result = _reportServerExecutionService.Render(reportFormat, devInfo.ToString(),out extension, out encoding, out mimeType, out warnings, out streamIds);
After the render, the byte[] should contain your report and once it has been displayed on a web page the embedded images should now be sourced to your temp location that is accessible to your web app.
EDIT :
Also, I noticed that you are trying to do some sort of post processing to the content that is returned from Render(). You do not have to touch that at all. Since you told SSRS to replace the image sources via the StreamRoot property then the renderer can handle it from there.
The only steps needed to re-path your report's assets:
Let SSRS know where you plan to place the assets it will be referencing in the report.
Intercept the report streams and save to an accessible location specified in the step above.
NOTE :
Here are some ways to get a virtual and physical temp folder from the context of your web app..
//Virtual Temp Folder - MVC
System.Web.HttpContext.Current.Request.Url.GetLeftPart(UriPartial.Authority) + Url.Content("~/Temp/");
//Virtual Temp Folder - Non-MVC
VirtualPathUtility.ToAbsolute("~/Temp/");
//Physical Temp Folder
AppDomain.CurrentDomain.BaseDirectory + #"Temp\";
Below isway I achieve render report using reporting services (ReportExecutionSerivce class and webrefrence of SSRS)
public class ReportManager
{
private readonly ReportExecutionService _reportServerExecutionService;
public ReportManager(string reportServerWsdlUrl, string username, string password, string domain)
{
_reportServerExecutionService = new ReportExecutionService
{
Url = reportServerWsdlUrl,
Credentials = new NetworkCredential(username, password)
};
}
public string Render(string reportDirectory, string reportName, string reportFormat, ParameterValue[] parameters)
{
_reportServerExecutionService.ExecutionHeaderValue = new ExecutionHeader();
_reportServerExecutionService.LoadReport("/GES-MVC/"+reportName, null);
_reportServerExecutionService.SetExecutionParameters(parameters, "en-us");
string encoding;
string mimeType;
string extension;
Warning[] warnings;
string[] streamIds;
var result = _reportServerExecutionService.Render(reportFormat, #"<DeviceInfo><StreamRoot>/</StreamRoot><HTMLFragment>True</HTMLFragment></DeviceInfo>", out extension, out encoding, out mimeType, out warnings, out streamIds);
//Here is logic for image replcaement
string html = string.Empty;
html = System.Text.Encoding.Default.GetString(result);
html = GetReportImages(_reportServerExecutionService, reportFormat, streamIds, html);
return html;
}
public string GetReportImages(ReportExecutionService _reportServerExecutionService, string reportFormat, string[] streamIds, string html)
{
if (reportFormat.Equals("HTML4.0") && streamIds.Length > 0)
{
string devInfo;
string mimeType;
string Encoding;
string fileExtension = ".jpg";
string SessionId;
Byte[] image;
foreach (string streamId in streamIds)
{
SessionId = Guid.NewGuid().ToString().Replace("}", "").Replace("{", "").Replace("-", "");
string reportreplacementname = string.Concat(streamId, "_", SessionId, fileExtension);
html = html.Replace(streamId, string.Concat(#"Report\GraphFiles\", reportreplacementname));
devInfo = "";
image = _reportServerExecutionService.RenderStream(reportFormat, streamId, devInfo, out Encoding, out mimeType);
System.IO.FileStream stream = System.IO.File.OpenWrite(HttpContext.Current.Request.PhysicalApplicationPath + "Report\\GraphFiles\\" + reportreplacementname);
stream.Write(image, 0, image.Length);
stream.Close();
mimeType = "text/html";
}
}
return html;
}
and here I pass required parameters to class
string rprwebserviceurl = exceservice;
string ReportDirName = "GES-MVC";
string ReportName = "GES_FWCR";
string RptFormat = "HTML4.0";
ParameterValue[] parameters = new ParameterValue[5];
parameters[0] = new ParameterValue();
parameters[0].Name = "PlantID";
parameters[0].Value = PlantID;
parameters[1] = new ParameterValue();
parameters[1].Name = "FromDateTime";
parameters[1].Value = Convert.ToString(fromDate); // June
parameters[2] = new ParameterValue();
parameters[2].Name = "ToDateTime";
parameters[2].Value = Convert.ToString(Todate);
parameters[3] = new ParameterValue();
parameters[3].Name = "ClientID";
parameters[3].Value = ClientID;
parameters[4] = new ParameterValue();
parameters[4].Name = "SelectedFeeders";
parameters[4].Value = SelectedFeeders;
ReportManager rpt = new ReportManager(rprwebserviceurl,RptUserName,RptPassword, "localhost");
res = rpt.Render(ReportDirName, reportName, RptFormat, parameters);

How do I customize the name of a report in SSRS 2016 to be output?

I want to export a paginated report from SSRS 2016 with a custom name from code. I can do it if I use the old 2005 control, but when I use the new URL access it either prompts me (if I'm in Edge) but defaults to the name of the report or in Chrome it just downloads with no prompting.
The report name, for example, is MyTestReport with several parameters passed to it. I'd like to be able to use those parameters to set the filename.
http://localhost/ReportServer/Pages/ReportViewer.aspx?/Finance/MyTestReport&i_entityID=98&i_sy=2016&i_runType=3&i_isPreview=true&rs:Format=PDF
That URL would ideally create a filename of 2016_Preview_Report.pdf if possible. I've searched through the SSRS documentation but can't find anything on how to go about doing so. A section of the code I'm using to export to PDF using the old 2005 control is below:
IReportServerCredentials irsc = new CustomReportCredentials(userid, password, domain);
var parametersCollection = new List<ReportParameter>();
parametersCollection.Add(new ReportParameter("i_sy", SY.ToString(), false));
parametersCollection.Add(new ReportParameter("i_entityID", LEA.ToString(), false));
parametersCollection.Add(new ReportParameter("i_runType", runtype.ToString(), false));
parametersCollection.Add(new ReportParameter("i_isPreview", isPreview.ToString(), false));
ReportViewer rv = new Microsoft.Reporting.WebForms.ReportViewer();
rv.ProcessingMode = ProcessingMode.Remote;
rv.ServerReport.ReportServerCredentials = irsc;
rv.ServerReport.ReportPath = REPORT_PATH;
rv.ServerReport.ReportServerUrl = new Uri(SSRS_REPORT_SERVER);
rv.ServerReport.SetParameters(parametersCollection);
rv.ServerReport.Refresh();
byte[] streamBytes = null;
string mimeType = "";
string encoding = "";
string filenameExtension = "PDF";
string[] streamids = null;
Warning[] warnings = null;
FileContentResult ReturnFile = null;
filenameExtension = ExportType;
mimeType = "application/pdf";
streamBytes = rv.ServerReport.Render("PDF", null, out mimeType, out encoding, out filenameExtension, out streamids, out warnings);
ReturnFile = File(streamBytes, mimeType, filename + "."+filenameExtension);
return ReturnFile;
This is how I did it:
public ActionResult GetPDFReport(int? id)
{
string filename = "Generate Filename Here"
NetworkCredential nwc = new NetworkCredential("username", "password");
WebClient client = new WebClient();
client.Credentials = nwc;
string reportURL = "http://servername//ReportServer?PO&rs:Format=PDF&rs:ClearSession=true&Param1=" + id;
return File(client.DownloadData(reportURL), "application/pdf", filename);
}

Prompts Login window in Crystal Report in ASP.NET

I am using VS 2012
MySql
mysql-connector-odbc-5.3.4-win32.msi
4.crystal report runtime on windows server 2008.
My web application works fine in my development system, but after deployment to Windows server 2008 , crystal reports ask for addition information about login information as given in following screen.
using the following code.
string databaseName = "hr";
string serverName = "192.168.137.6";
string userID = "co";
string pass = "password";
protected void btn_search_Click(object sender, EventArgs e)
{
CrystalReportViewer1.Visible = true;
ReportDocument reportDocument = new ReportDocument();
TableLogOnInfo TabLogOnInfo = new TableLogOnInfo();
TableLogOnInfos TabInfos = new TableLogOnInfos();
ConnectionInfo conInfo = new ConnectionInfo();
string reportPath = Server.MapPath(#"~/GeneralEmpReports/ddoWiseEmpRpt.rpt");
string ddoCode = tbx_ddoCode.Text.ToUpper();
reportDocument.Load(reportPath);
reportDocument.SetParameterValue("D", ddoCode);
conInfo.ServerName = serverName;
conInfo.DatabaseName = databaseName;
conInfo.UserID = userID;
conInfo.Password = pass;
conInfo.AllowCustomConnection = false;
conInfo.IntegratedSecurity = false;
foreach (CrystalDecisions.CrystalReports.Engine.Table T in reportDocument.Database.Tables)
{
TabLogOnInfo = T.LogOnInfo;
TabLogOnInfo.ConnectionInfo = conInfo;
T.ApplyLogOnInfo(TabLogOnInfo);
}
CrystalReportViewer1.ReportSource = reportDocument;
CrystalReportViewer1.ReuseParameterValuesOnRefresh = true;
CrystalReportViewer1.AutoDataBind = true;
CrystalReportViewer1.Zoom(80);
}
i don't know how to solve the issue.

HTTP Get to Report Server 2008 works with DefaultCredentials, fails with some NetworkCredentials

The following WithDefaultCredentials() works but WithCredentialsMe() fails with a http 401 returned ?
The difference is that
ICredentials credentials = System.Net.CredentialCache.DefaultCredentials;
works OK against the report server 2008 url , but
ICredentials credentials = new NetworkCredential("myUsername", "myPassword", "ourDomain");
comes back with a HTTP 401.
The console app is being developed by me so, there should not be a difference between DefaultCredentials and NetworkCredential. There is no problem with my Username and password.
Any ideas ?
static void Main(string[] args)
{
WithDefaultCredentials();
WithCredentialsMe();
}
public static void WithDefaultCredentials()
{
try
{
ICredentials credentials = System.Net.CredentialCache.DefaultCredentials;
string url = "http://myBox/ReportServer_SQLSERVER2008/Pages/ReportViewer.aspx?%2fElfInvoice%2fElfInvoice&rs:Command=Render&InvoiceID=115abba9-61bb-4070-bd28-f572115a2860&rs:format=PDF";
var bytes = GetByteListFromUrl(url, credentials);
File.WriteAllBytes(#"c:\temp\A_WithDefaultCredentitials.pdf", bytes.ToArray());
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
public static void WithCredentialsMe()
{
try
{
ICredentials credentials = new NetworkCredential("myUsername", "myPassword", "ourDomain");
string url = "http://myBox/ReportServer_SQLSERVER2008/Pages/ReportViewer.aspx?%2fElfInvoice%2fElfInvoice&rs:Command=Render&InvoiceID=115abba9-61bb-4070-bd28-f572115a2860&rs:format=PDF";
var bytes = GetByteListFromUrl(url, credentials);
File.WriteAllBytes(#"c:\temp\A_Credentials_me_1.pdf", bytes.ToArray());
}
catch( Exception ex )
{
Console.WriteLine( ex.Message);
}
}
public static List<Byte> GetByteListFromUrl(string url, System.Net.ICredentials credentials)
{
List<Byte> lstByte = new List<byte>();
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
if (credentials != null)
{
request.Credentials = credentials;
}
var response = (HttpWebResponse)request.GetResponse();
var stream = response.GetResponseStream();
int totalBytesRead = 0;
int bufferbytesRead = 0;
try
{
byte[] buffer = new byte[1024];
while ((bufferbytesRead = stream.Read(buffer, 0, buffer.Length)) > 0)
{
totalBytesRead += bufferbytesRead;
if (bufferbytesRead < buffer.Length)
{
bufferbytesRead = bufferbytesRead - 1 + 1;
}
for (int i = 0; i < bufferbytesRead; i++)
{
var bToAdd = buffer[i];
lstByte.Add(bToAdd);
}
}
}
catch (Exception ex)
{
}
finally{}
//-Return
return lstByte;
}
With the help of http://forums.asp.net/t/1217642.aspx this code got me what I wanted ...
Next step is clean it all up and unit test in dev ...
public static void ReportServerWebService()
{
// wsdl /out:rs.cs /namespace:ReportService2005 http://mybox/ReportServer_SQLSERVER2008/ReportService2005.asmx?wsdl
/// wsdl /out:rsExec.cs /namespace:ReportExecution2005 http://mybox/ReportServer_SQLSERVER2008/ReportExecution2005.asmx?wsdl
ICredentials credentials = new NetworkCredential("myUserName", "myPassword", "hcml");
Guid invoiceID = new Guid("115ABBA9-61BB-4070-BD28-F572115A2860");
var rs = new ReportService2005.ReportingService2005();
var rsExec = new ReportExecution2005.ReportExecutionService();
rs.Credentials = credentials;
rsExec.Credentials = credentials;
string historyID = null;
string deviceInfo = null;
string format = "PDF";
Byte[] bytPDF;
string encoding = String.Empty;
string mimeType = String.Empty;
string extension = String.Empty;
ReportExecution2005.Warning[] warnings = null;
string[] streamIDs = null;
string _reportName = "/ElfInvoice/ElfInvoice" ;
string _historyID = null;
bool _forRendering = false;
ReportService2005.ParameterValue[] _values = null;
ReportService2005.DataSourceCredentials[] _credentials = null;
ReportService2005.ReportParameter[] _parameters = null;
try
{
// Get if any parameters needed.
_parameters = rs.GetReportParameters( _reportName, _historyID, _forRendering, _values, _credentials);
// Load the selected report.
var ei = rsExec.LoadReport(_reportName, historyID);
// Prepare report parameter.
// Set the parameters for the report needed.
var parameters = new ReportExecution2005.ParameterValue[1];
// // Place to include the parameter.
if (_parameters.Length > 0)
{
parameters[0] = new ReportExecution2005.ParameterValue();
parameters[0].Label = "InvoiceID";
parameters[0].Name = "InvoiceID";
parameters[0].Value = invoiceID.ToString();
}
rsExec.SetExecutionParameters(parameters, "en-us");
bytPDF = rsExec.Render( format , deviceInfo , out extension , out encoding , out mimeType , out warnings , out streamIDs ) ;
try
{
File.WriteAllBytes(#"c:\temp\A_WithMyCredentitials_ReportServerWebService.pdf", bytPDF.ToArray());
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}