Load SSRS Report from file in C# in a service - c#

We are looking into replacing Crystal with SSRS.
I would like to know if it is at all possible to load the .rdl or .rdl.data file in C# and generate the report to a memory stream.
I have seen some examples using the LocalReport, but this seems to be part of either the WinForms or WebForms assemblies.
So what I would like to know is:
Is it possible to load the report from file as part of our service.
Can we then generate the report to a Stream (lets say a memory
stream)
Can I do this without using the WebForms/WinForms assemblies in my
service
Can we achieve this without using the webservice for SSRS

I'm not sure that this is an answer, but lets call it supporting material.
I have this code example from msdn that shows how you can do this by creating a service client and calling a given report as a PDF and saves it to file stream.
http://msdn.microsoft.com/en-us/library/reportexecution2005.reportexecutionservice.render.aspx
The problem I'm currently having is finding the correct client object to interact with after pointing VS to the SSRS service. The object I'm using to interact with the service is:
ReportExecutionServiceSoapClient rs = new ReportExecutionServiceSoapClient();
However, the interface doesn't match my code example. So this is a little closer, but not an answer.
UPDATE: The correct Proxy class generator
Here's the link to how to generate the proxy correctly. You'll need the windows sdk installed (current is 7.1). You can find that on microsoft.com, like I did. Execute the command line and it'll generate a file for you. Include in project:
http://msdn.microsoft.com/en-us/library/ms155134%28v=SQL.110%29.aspx
UPDATE: Got the thing workin
I just had to generate the correct proxy. Ok, so for SSRS 2010, apparently they split report execution and management out into two services. The only one I needed to generate my report from a C# console app was the execution service. Maybe that's totally obvious to everyone but me :) ?
Ok so open up a Windows SDK command shell and put this stuff in it for the execution service:
wsdl /language:CS /n:"Microsoft.SqlServer.ReportExecution" http://<Server Name>/reportserver/reportexecution2010.asmx?wsdl /o:"ReportExecution.cs"
Go to C:\Program Files\Microsoft SDKs\Windows\v7.1 and pick up your ReportExecution.cs file. Copy and paste it in your project.
Then you just have to say this:
Microsoft.SqlServer.ReportExecution.ReportExecutionService rsExec =
new Microsoft.SqlServer.ReportExecution.ReportExecutionService();
rsExec.Credentials = System.Net.CredentialCache.DefaultCredentials;
rsExec.Url = #"http://<ServerName>/reportserver/ReportExecution2005.asmx";
Follow along the example from this link, which is the same one as above, and you should be generating some pretty awesome reports from your handy C# app.

Related

Can a ReportViewer pull data by itself on local mode?

I was tasked with making a Webpage (aspx), which automaticly reads rdlcs, and generates a webpage, with the parameters at the top as webelements and the report as the main part of the page.
So far, I have tried reading the file as an XML-Doc, and just parsing the info out of there. But this may be done simpler. (I have no expirience with reports or rdl(c) files).
I have seen that there is a DataSets/DataSet/Query/CommandText-Tag, which can hold an SQL-Statement. Now this let's my boss and myself assume, that it is possible to make it already deliver this info by itself, which me coding this. On the other hand, I see nowhere any example for that.
My current code looks like this:
private string rdlcFilepath = "some/path/to/file.rdlc";
protected void Page_Load(object sender, EventArgs e) {
string sql = GetSqlStatementFromRdlcFile(rdlcFilepath);
DataTable dtTest = DatabseFacade.Execute_SQL(sql);
MainReportViewer.LocalReport.ReportPath = Server.MapPath(rdlcFilepath);
MainReportViewer.ProcessingMode = ProcessingMode.Local;
MainReportViewer.LocalReport.DataSources.Add(new ReportDataSource("DataSet1", dtTest));
MainReportViewer.LocalReport.Refresh();
}
So, I have 2 theories:
The CommandText-Tag tag is a ment for a "report server" and should be used only in ProcessingMode.Remote, and is not relevant when in Local mode.
I'm approaching this whole thing wrong.
If 2 is true, then probably the problem is manually adding the dtTest, and it should have some other instruction to make the report-element "pull" the data by itself.
My questions:
Is one of my assumptions correct, or what is going on?
Any other hints/links that may help?
I may note, that every tutorial/example I saw on the internet, that used ProcessingMode.Local, used an "external" datatable, and the LocalReport.DataSources.Add way.
Just for clearification, our (my boss' and my) ideal solution, would be some "magic" command, that makes the ReportViewer, use the information in the rdlc file, to connect to the database, and display the result. After all it contains all of the info, from connection-string to SQL-statement.
Please note that the rdl file is the Native SSRS report version, which is faster and easier to develop. The type of Project needed here is "Reporting Services Project", while the rdlc is the client side of the rdl file which is usually developed in normal visual studio web or desktop project, which is of course used as local report and usually takes more time to develop and you have to provide all DataSources, DataSets and Parametrs if there is any.
In my opinion, there is much simpler solution to your problem. You can actually setup remote or local SSRS reporting services server and this will enable you to work on the reports(rdl files) natively, which is basically cleaner and faster. In terms of performance too, I think that native mode scales out and outperform the local or client report option (.rdlc). Using this approach, you don't have to add DataSources or Datasets or Parametrs as all of this you will configure natively and use the configuration manager to configure Shared DataSources and Datasets. You will only have to authinticate the use in your page and provide the URI of your SSRS server, User name, password and report path.
To know more about configuring SSRS Server use this link please:
SQL Server Reporting Service Configuration Manager
there are also a lot of links online.
You can authinticate the user like the below code sample shows:
// Set the processing mode for the ReportViewer to Remote
ReportViewer1.ProcessingMode = ProcessingMode.Remote;
ServerReport serverReport = ReportViewer1.ServerReport;
ReportViewer1.ServerReport.ReportServerCredentials = new CustomReportCredentials("username", "password", "domain/Ip");
serverReport.ReportServerUrl =
new Uri("http://xx.xxx.xxx.222/ReportServer_MSSQLSERVER2016");
serverReport.ReportPath = "/Reports/Report3";
ReportViewer1.ServerReport.Refresh();
Here is a good link about Passing Credentials to Sql Report Server 2008
Passing Credentials to Sql Report Server 2008
That's all you need to do. just drag a report viewer and authenticate the user and that's it. hopefully this is helpful for you.

Debenu PDF works on localhost fails on azure

I'm using Debenu PDF Library to extract pages from a pdf file. Here is how I do it,
var pdflib = new PDFLibrary(LoadDll());
int result = pdflib.UnlockKey("UNLOCKKEYISHERE");
AzureStorageWrapper sasWrapper = new AzureStorageWrapper(ConfigurationManager.AppSettings["AzureStorageConnection"], "cont1");
byte[] blob = sasWrapper.GetBlob("file.pdf");
pdflib.LoadFromString(blob, "");
byte[] page = pdflib.RenderPageToString(50, 1, 1);
When I run this on my local machine it works perfectly (first page of the PDF file comes to the page byte array).
But after publishing this as an Azure Web App page gets a some useless string of bytes.
Can anyone explain to me why this is?
You've hit an Azure App Service sandbox runtime exectution limitation.
From https://github.com/projectkudu/kudu/wiki/Azure-Web-App-sandbox#unsupported-frameworks:
Unsupported frameworks
Here is a list of frameworks and scenarios that have been found to be not be usable due to one or more of the restrictions above. It's conceivable that some will be supported in the future as the sandbox evolves.
PDF generators failing due to restriction mentioned above:
EVOPDF
Rotativa
wkhtmltopdf
Syncfusion
Siberix
NReco (uses wkhtmltopdf)
Spire.PDF
Other scenarios:
PhantomJS/Selenium: tries to connect to local address, and also uses GDI+.
It's probably safe to say you can add Debenu PDF to that list.
There is however a mention that some GDI calls may work on Basic/Standard pricing tiers in App Service. It's worth giving that a go if you're currently on Free/Shared.
Alternatives to App Service for running stuff that uses GDI/GDI+:
A Web/Worker Role (Cloud Services)
Service Fabric
IaaS Virtual Machine
Similar question here:
What could cause EvoPDF "unable to render html" exception when deployed to Azure Website

Use external xml file after publishing the c# desktop application

I have developed a c# desktop application that needs to be hosted on a server and will be scheduled to fetch data based on queries stored in XML files. while developing, I was using the following code to read XML files:
var query = new XPathDocument(#"C:\\Documents and Settings\\XYZ\\Desktop\\productplanningquery.xml");
as you can see I had put the XML file conveniently on my desktop and it worked fine while development. What I want to do now, is to give at a path such that where ever I host the application plus the XML files, it does not throw an exception. One way i thought could be to have a folder in a directory where the application will be installed but for that i will have to figure out the path to current directory dynamically (which i could not figure out).
Please help.
You could pass the location of you XML using args this way you're code would look like so:
var query = new XPathDocument(args[0])
You can also use relative path. Make sure that when deploying your code you keep the location of the file in the same relative location. For example if you place the XML in the same directory as the application
var query = new XPathDocument("productplanningquery.xml")
I am not sure what you want to achieve whether you want to read xml using winform app and do some operation and then pass it web app or some thing else. But here is my understandings:
Case 1: If you need to create XML outside the IIS and that XML will be consumed by ASP.Net app, then :
For using a desktop application with IIS server , you need to have full administrative access to the Live Machine. If its not then you should consider building windows services to operate on the XML files or any task that will run behind the scenes to decrease the load of the asp.net app.
Still in this case if you dont own a server then you need some Virtual Private Hosting or similar kind of hosting where you have almost all previleges to access the system. Then deploy the Windows Service, set the output path in such a manner so that it can be accessed by asp.net app too. And do whatever you want.
Case 2: If you want o read XML in ASP.Net Solely, then
In this case you case read it easily by using XDocument.But note, XML should in the same application directory or under the reach of the ASP.Net app
MSDN Article for Web-Windows Services with ASP.Net
You can use something like this:
var path = string.Format("{0}\\{1}", Environment.GetFolderPath(Environment.SpecialFolder.Desktop), "productplanningquery.xml");
var pathForCurrentApp = string.Format("{0}\\{1}", Environment.CurrentDirectory, "productplanningquery.xml");

How can I debug this web service?

I have a simple web service that looks something like this:
[WebMethod]
public OrderForecastItem GetOrderForecast(int shipTo, string catalogName, bool showPricing)
{
return OrderForecastManager.GetOrderForecast(shipTo, catalogName, showPricing);
}
I'm calling it from another place in a fairly simple way:
using (OrderForecastWS.OrderForecastWS service = new OurSite.Web.Reporting.OrderForecastWS.OrderForecastWS())
{
OrderForecastItem orderForecastItems = service.GetOrderForecast(2585432, "DENTAL", false);
}
After some gymnastics to get the systems to understand that I'm talking about the same type of objects on the client and server sides (I had to open the Reference.cs file inside my Web References, delete the generated OrderForecastItem and add a link to our real OrderForecastItem), the system runs and attempts to get the item.
Unfortunately, it now bombs during the service call, claiming:
Exception There is an error in XML document (1, 1113).(InvalidOperationException)
I can go to the web service in a browser, put in the same values, and I get a seemingly valid XML response. (It looks okay to me, and I ran it through the XML parser at W3Schools, and it cleared it.)
I think the numbers in the error are supposed to be the line and character number...but the browser seems to reformat the xml document, so I can't easily see what the original (1, 1113) location is.
I don't see an easy way to intercept the response and examine it, since it seems to be blowing up as soon as it gets it.
How can I debug this?
If you control the service, you can step into it. If it is a part of your solution and hosted in VS WebDev on your local box, just F11 from Visual Studio, if service is hosted remotely (eg by IIS on other computer) run remote debugging tool on service host msdn, and then you will be able to step in to the service remotely.
By the way, you can tell Visual Studio to re-use objects from referenced libraries for types from the service: just pick configure Service Reference from service context menu and tell which libraries to re-use.
On second thought this error may happen if returned XML could not be deserialized into your business object. May happen when class is changed on either side, or you are trying to use different version of business library than service is using.
If you use Firefox, I'd recommend Firebug. You'll be able to easily view the response from the website in its original format, which might get you closer to the line and position you're looking for.

IIS Permissions for Saving Word Documents

Our ASP.NET/C# lets users edit and manage Word (OpenXML) documents that are hosted on a server. I am using client-side VBScript functions to handle some of the editing functions including saving the document to a folder on the server. For the save functionality, I am using the following function call :
Document.SaveAs "http://server/savefolder/savefile.docx"
I have given "Full Control" permissions on savefolder to both the NETWORK SERVICE and the IUSR_MACHINE users. Yet the above call fails. The error number returned is 5096. The error message is some gibberish that doesn't make any sense.
The server is Windows 2003 and the IIS version is 6.0. I have installed the OpenXML SDK 2.0 CTP on the server.
I can successfully read and print documents.
Does anyone tell me what I am doing wrong? or what additional settings need to be in place?
BTW, the error message ("gibberish" from my post) is:
"EOALPHABETICARABICARABICABJADARABICALPHABAHTTEXTCAPSCARDTEXTCHARFORMATCHI"
No, I am not making this up!
In my case, that error 5096 with description "EOALPHABETICARABICARABICABJADARABICALPHABAHTTEXTCAPSCARDTEXTCHARFORMATCHI"
occurred when using VBA code in Access to drive a Word mail-merge. The cause was trying to save a document with the same name (including path) as an open document.
Error line:
objApp.ActiveDocument.SaveAs saveAsName
where objApp is the object variable representing the Word application and saveAsName is the string variable storing the name I am trying to save the file as e.g. "C:\temp\testdoc.docx".
IF a file with the same name exists but is not open, the above code overwrites it silently.
Turns out WebDAV is not turned on by default in IIS 6.0. Once I turned it on, I was able to save the documents just fine.
Thanks for all your answers!
Just a guess... if the vbscript is running on the client, the code is probably running under the user's account, not under the server's IIS account. So unless you give write access to that user, vbscript probably won't work for this.
Since you're using ASP.NET, you could try writing a web service that takes in Word document data and saves it to the server for you.
I'd try running Fiddler on the client while trying to save the document to get a sense of what's really going on. I wonder if maybe it's trying to do an HTTP PUT (as opposed to a POST).
Have you given write access to the folder in IIS manager?
Is the save folder you're using outside of the websites root directory, i.e. 'hidden' from the internet?
Just to add to SI's information...
I also get this I get the 5096 - EOALPHABETICARABICARABICABJADARABICALPHABAHTTEXTCAPSCARDTEXTCHARFORMATCHI error when my code tries to save a MS Word document with the same name and to the same location as a Word document that is already open in another instance of Word.
Although not entirely relevant to this thread, I hope it may help someone else who stumbles upon this thread!
Regards,
Duane,
this question is old but still active ?
You save the file with a http://... url, i think you should save it with a file URL as
Document.SaveAs "\\server\savefolder\savefile.docx"
Grtz

Categories

Resources