How to handle ReportViewerWebPart report printing error? - c#

I’m implementing a solution based on SharePoint 2010 and MS Reporting Server. I’m experiencing a problem with ReportViewerWepPart. I have a scenario where I need to display a custom error when a report cannot be printed. Unfortunately, unlike ReportViewer asp control, ReportViewerWepPart does not have any properties/events indicating that there is an error and the report cannot be printed. After spending some time on the problem I came with a solution using reflection. I discovered that ReportViewerWepPart uses internally ReportViewer and I attached to ReportError event on this private internal component. Here is my code:
…
try
{
ReportViewer rv = (reportViewer.GetType().GetField("m_reportViewer", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance).GetValue(reportViewer) as ReportViewer);
rv.ReportError += new Microsoft.Reporting.WebForms.ReportErrorEventHandler(ReportWidgetControl_ReportError);
}
catch(Exception e)
{
LogHandler.LogError(e, "Unable to attach ReportViewerWebPart error hadler.");
}
…
void ReportWidgetControl_ReportError(object sender, Microsoft.Reporting.WebForms.ReportErrorEventArgs e)
{
reportViewer.Visible = false;
HandleError();
}
Unfortunately this solution is a hack in the web part. Do you think that using a reflection in that way can cause any problems? Am I missing something, Is there another way to see if report is printed?

This is fine, but I would be careful catching all exceptions.
It looks like you are hiding the reportViewer and calling your HandleError code no matter what the error. There may be exceptions that occur that are minor and are handled without issue internally and hiding the reportViewer object might not be appropriate.
I don't know what your HandleError code does but I would suggest quietly logging the error to a log table or file until you spot the exact printing error you are trying to handle, and then only worrying about handling that.

Related

Response.write in application_error not working?

Ok, I have a weird problem and can't find anything about it online. I'm trying to get custom application-level error handling working in ASP.NET. I have customErrors turned off in the web.config with the hopes of handling everything in application_error. Bear with me...
My code in global.asax is very simple:
void Application_Error(Object sender, EventArgs e) {
HttpContext.Current.Trace.Write("ERROR MESSAGE");
Response.TrySkipIisCustomErrors = true;
var error = Server.GetLastError();
HttpContext.Current.Response.Write("ERROR MESSAGE");
HttpContext.Current.ClearError();
}
I created a simple aspx page and threw an error in Page_Init or Page_Load, and everything worked as expected, i.e.: I see "ERROR MESSAGE" on a blank page when an error occurs.
Now I dynamically add some user controls to that aspx page and everything renders as expected. If I then throw an error from INSIDE one of the controls, I only get a blank white page. "ERROR MESSAGE" does not appear.
Now I know that application_error is still firing because when I remove the call to ClearError(), I get a Yellow Screen Of Death. Also, I can execute a Server.Transfer in there and that works fine. But nothing will come out for Response.Write.
This goes further: I can set Response.StatusCode, but a Response.Redirect will error out (and thus throw me into an infinite loop). Trying to write to the Event Log also errors out, but instead of throwing a new error, it throws the original, i.e.: "Input string was not in a correct format." when I try to convert a string to a number. As mentioned, Response.Write doesn't do anything, though it does not throw an error.
So looking at my trace log, in the second case (exception inside dynamically added user control) I see a full control tree and the error occurs right after Begin Render. In the first case, the tree is empty and the error is thrown either after Init or Load. Both times, trace.axd reports Unhandled Execution Error.
When I move the throw inside the control to the control's constructor or OnInit, things work as expected. When I move it to OnLoad or Render, it gets goofy.
So I'm wondering if at some point the Response object loses certain functionality. I've tried all sorts of permutations, from syntax (using HttpContext.Current.Response vs Context.Response vs pulling the Response object from the "sender" parameter), to moving the ClearError() or Response.Clear(), etc methods around, etc. I've tested the Response object for "null-ness" as well, and it never reports a null. I can set some response properties (http status code) but not others.
I'm using IIS7.5 integrated mode (.NET v4), but experienced similar problems when I tried Classic mode.
So I'm trying to solve this mystery, obviously, but my goal is to ultimately handle all errors, no matter what point in the asp.net lifecycle they occur, and to be able to write out some information from the handler (ie application_error).
Handled unhandled exceptions using this approach. Custom error is off in web.config.
All 3 options work.
void Application_Error(object sender, EventArgs e)
{
// Code that runs when an unhandled error occurs
Response.TrySkipIisCustomErrors = true;
this.Server.ClearError();
this.Server.GetLastError();
//DO SOMETHING WITH GetLastError() may be redirect to different pages based on type of error
//Option 1:
Response.Write("Error");
//Option 2:
Response.Redirect("~/Error.aspx");
//Option 3:
this.Server.Transfer("~/Error.aspx");
}

Windows Form Won't Display in Debug Mode

I recently upgraded to VS 2012. I have a set of coded UI tests that I've coded in VS 2010 and I'm trying to spin them up in VS 2012. I have a windows form that I'm displaying at the beginning of the test run by using the AssemblyInitialize attribute. I use this form to allow users to select from sets of values and those values are used to data feed the tests. Here's a copy of my code that displays the form:
[AssemblyInitialize]
public static void AssemblyInitialize(TestContext context)
{
ProcessUtility.TerminateAll();
if (!File.Exists(Directory.GetCurrentDirectory() + #"\RunInfo.ser"))
{
InitializeForm initForm = new InitializeForm();
initForm.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen;
initForm.ShowDialog();
}
}
So, here's my headache: the form displays just fine in Run mode. However, if I try to spin it up in Debug mode, it never displays. I've stepped through the code. It's loading all of the controls for the form with no errors. I make it to the 'initForm.ShowDialog()' line of code. It runs that line of code but then nothing happens. I don't receive any errors and the status in the lower left of the IDE is 'Ready'. It's almost as if the IDE thinks the form is displayed but it's not. I've double-checked the Task Manager and it's just not there. I've verified the build configuration is set to Debug. I've tried cleaning the solution and re-building. This code continues to work in VS 2010. Please tell me someone out there has ran into a similar problem because I'm out of ideas. I'm new to stackoverflow so let me know if there is anything else I can provide to better explain the issue. Thank you in advance for taking a look at it.
Not sure why this solution works, but I was able to solve this issue in VS2013 by setting the visible property on the form I was trying to display to true and then false before calling ShowDialog.
VB.Net example code
Dim form as Form = new Form
form.Visible = True
form.Visible = False
form.ShowDialog
I was able to get the form to display using the following code instead of ShowDialog. I still have no idea why ShowDialog wasn't working but this does the trick:
InitializeForm initForm = new InitializeForm();
initForm.Visible = true;
initForm.Focus();
Application.Run(initForm);
Most likely a exception is happening during the initialization, Go in to the Debug->Exceptions dropdown menu and be sure the checkbox thrown for Common Language Runtime Exceptions is checked, this will let your code break on the exception that is happening.
If you are still not catching the exception go to Debug->Option and Settings then uncheck the box for Enable Just My Code and check the box for Break when exceptions cross AppDomain or managed/native boundries
This may give you some "read herring" exceptions, as some .NET processes use exceptions for control of flow logic. So just be aware that the first exception you see may not be the cause of your problem.
I was experiencing the same thing while debugging an old code and resolved the situation by adding [STAThread] attribute on top of container method which contains form.ShowDialog();
For example:
[STAThread]
public void MessageBoxShow(string errorMessage)
{
using (frmError errorForm = new frmError(errorMessage))
{
errorForm.ShowDialog();
}
}
This has solved any hanging occured while hitting-continuing debug point.
Platform Windows 7 x64 enterprise edition and VS2008 (both has latest updates as of today).
Hope this helps.
Update 1: Please ignore using statement in example since I am using a custom form which inherits IDisposable in addition to Windows.Form and has custom disposition routines. Sorry if it has created any confusion.

"Callback Error: Invalid response from server" from C# ASP.Net application

I have an ASP.Net application with a button containing the following Javascript to be invoked when it is clicked:-
function calculate() {
sectionIndex = getSelectedRadioIndex("section");
compositionIndex = getSelectedRadioIndex("composition");
CallBackOU.callback( "calculate" , sectionIndex, compositionIndex );
}
I can verify that control reaches the last line of this function by setting a breakpoint on it. But instead of invoking the method in the code-behind file...
protected void CallBackOU_Callback (object sender, ComponentArt.Web.UI.CallBackEventArgs e)
{
//blah blah
}
I get a dialogue reporting
Callback Error: Invalid response from server.
This dialogue appears three times, after which the page sits there doing nothing (forever, so far as I can make out).
I can't find any information about this. Can anyone give me any clues or pointers about how to go about diagnosing the problem?
Without seeing the signature of the calculate callback method this is only a shot in the dark but some issues i have encounter when invoking web methods from javascript are make sure the method is properly decorated [WebMethod], make sure the method is static, make sure the parameters are of the correct type and named properly (they are infact case sensitive when deserializing JSON iirc). A little more information regarding how the call is made (JSON/XML) and the signature might help. Also, you can try using fiddler to see if you get any more information regarding the error.

Completed Event not triggering for web service on some systems

This is rather weird issue that I am facing with by WCF/Silverlight application. I am using a WCF to get data from a database for my Silverlight application and the completed event is not triggering for method in WCF on some systems. I have checked the called method executes properly has returns the values. I have checked via Fiddler and it clearly shows that response has the returned values as well. However the completed event is not getting triggered. Moreover in few of the systems, everything is fine and I am able to process the returned value in the completed method.
Any thoughts or suggestions would be greatly appreciated. I have tried searching around the web but without any luck :(
Following is the code.. Calling the method..
void RFCDeploy_Loaded(object sender, RoutedEventArgs e)
{
btnSelectFile.IsEnabled = true;
btnUploadFile.IsEnabled = false;
btnSelectFile.Click += new RoutedEventHandler(btnSelectFile_Click);
btnUploadFile.Click += new RoutedEventHandler(btnUploadFile_Click);
RFCChangeDataGrid.KeyDown += new KeyEventHandler(RFCChangeDataGrid_KeyDown);
btnAddRFCManually.Click += new RoutedEventHandler(btnAddRFCManually_Click);
ServiceReference1.DataService1Client ws = new BEVDashBoard.ServiceReference1.DataService1Client();
ws.GetRFCChangeCompleted += new EventHandler<BEVDashBoard.ServiceReference1.GetRFCChangeCompletedEventArgs>(ws_GetRFCChangeCompleted);
ws.GetRFCChangeAsync();
this.BusyIndicator1.IsBusy = true;
}
Completed Event....
void ws_GetRFCChangeCompleted(object sender, BEVDashBoard.ServiceReference1.GetRFCChangeCompletedEventArgs e)
{
PagedCollectionView view = new PagedCollectionView(e.Result);
view.GroupDescriptions.Add(new PropertyGroupDescription("RFC"));
RFCChangeDataGrid.ItemsSource = view;
foreach (CollectionViewGroup group in view.Groups)
{
RFCChangeDataGrid.CollapseRowGroup(group, true);
}
this.BusyIndicator1.IsBusy = false;
}
Please note that this WCF has lots of other method as well and all of them are working fine.... I have problem with only this method...
Thanks...
As others have noted, a look at some of your code would help. But some things to check:
(1) Turn off "Enable Just My Code" under Debug/Options/Debugging/General, and set some breakpoints in the Reference.cs file, to see whether any of the low-level callback methods there are getting hit.
(2) Confirm that you're setting the completed event handlers, and on the right instance of the proxy client. If you're setting the event handlers on one instance, and making the call on another, that could result in the behavior you're describing.
(3) Poke around with MS Service Trace Viewer, as described here, and see if there are any obvious errors (usually helpfully highlighted in red).
Likely there are other things you could check, but this will keep you busy for a day or so :-).
(Edits made after code posted)
(4) You might want to try defining your ws variable at the class level rather than the function. In theory, having an event-handler defined on it means that it won't get garbage collected, but it's still a little odd, in that once you're out of the function, you don't have a handle to it anymore, and hence can't do important things like, say, closing it.
(5) If you haven't already, try rebuilding your proxy class through the Add Service Reference dialog box in Visual Studio. I've seen the occasional odd problem pop up when the web service has changed subtly and the client wasn't updated to reflect the changes: some methods will get called successfully, others won't.
(6) If you're likely to have multiple instances of a proxy client open at the same time, consider merging them into one instance (and use the optional "object userState" parameter of the method call to pass the callback, so you don't run into the nasty possibility of multiple event handlers getting assigned). I've run into nasty problems in the past when multiple instances were stepping on each other, and my current best practice is to structure my code in such a way that there's only ever one client instance open at a time. I know that's not necessarily what MS says, but it's been my experience.
This issue is because of special characters in one of the fields returned from DB which browser was not able to render. After considerable debug n search over the web, was able to find this out. Used Regular expressions to remove these special characters in WCF, the new returned values from the method was successfully rendered in various browsers on different system. :)
Make sure you have checked 'Generate asynchronous operations' in your service reference. Right-click on the service reference and check the box. This solved it for me.

Exception Handling in SCSF

I have a SCSF application i am trying to handle most of the exceptions using
Application.ThreadException += new ThreadExceptionEventHandler(new ThreadExceptionHandler().ApplicationThreadException);
The event handler :-
public class ThreadExceptionHandler
{
public void ApplicationThreadException(object sender, ThreadExceptionEventArgs e)
{
MessageBox.Show(e.Exception.Message, "An exception occurred:", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
Works fine . I can catch all the application exceptions in this block.
But the problem is after handling the exception the code again goes and executes the same exception generating code again. This happens till the time I get a windows message windows to send the error info to microsoft.
Could any one please help in telling me where I might be going wrong.
Thanks in Advance
Vikram
Note :- Currently i am throwing
New Exception("Test Exception"); from a button event. I am doing this to provide event handling in my application.
You have to set
Application.SetUnhandledExceptionMode(UnhandledExceptionMode.CatchException);
See this MSDN page for example code
But note that this kind of catch-all exception handling is not a good replacement for exception handling inside your logic. It is a good backup, but the best thing to do in a global handler is to log the information and exit. Your app could be in an unsafe/undefined state.
After some banging my head against the code I found that the problem was due to the fact that my SCSF solution had a winforms Shell and on that shell there were WPF usercontrols.
When the exception where generated on these WPF usercontrol (mostly the case) they are not caught by
Application.ThreadException coz Application class for WPF is different than that for Winforms.
In WPF application one need to handle Application.DispacherUnhandledException event.
Just my little finding ...
you would be surprised by just handling the Application.DispatcherUnhandledException. I have worked with SCSF which had WPF user controls. Read through this post . http://social.msdn.microsoft.com/forums/en-US/wpf/thread/c57cac13-f960-49a1-94b5-a3fd316ac4bc/ i would recommend handling AppDomain.UnhandledException too.

Categories

Resources