views:

41

answers:

2

Recently, I had a user control I was developing throw an exception. I know what caused the exception, but this issue got me thinking. If I have a user control throw an exception for whatever reason and I wish to replace that usercontrol with something else (e.g. an error saying, "Sorry, this part of the page broke.") and perhaps log the error, what would be a good way to do it that could be done independently of what the user control is or does (i.e. I'm not saying what the user control does/is, because I want an answer where that is irrelevant).

Code sample:

<asp:TableRow VerticalAlign="Top" HorizontalAlign="Left">
 <asp:TableCell>
  <UR:MyUserControl ID="MyUserControl3" runat="server" FormatString="<%$ AppSettings:RVUC %>"
   ConnectionString="<%$ ConnectionStrings:WPDBC %>" Title="CO" />
 </asp:TableCell>
 <asp:TableCell>
  <UR:MyUserControl ID="MyUserControl4" runat="server" FormatString="<%$ AppSettings:RVUA %>"
   ConnectionString="<%$ ConnectionStrings:WPDBA %>" Title="IEAO" />
 </asp:TableCell>
</asp:TableRow>
A: 

General ID: for ASP.NET it might work (not sure about ASP)

Before rendering each control - record it's id.

String CtrlID;

before each control:

CtrlID = control.name

put everything in try/catch (or do it to each control)

catch (Exception EX)
{
  hide(ctrlId)  (either set visible=false, or whatever suits you)
  show(error message)

}
Dani
I don't understand what you are suggesting.
Brian
before rendering a control, log it's name and if it fails, hide it.the reason you want to log it's name is to have a single catch statement. if you don't care to cover each control with try and catch, you don't need that. I use this technique when I have many controls, and I am too lazy to cover each one with try/catch.
Dani
I guess I just don't see what you mean by "Put everything in try catch." Using `<% %>` to wrap controls in try catch blocks doesn't actually work, and putting it in the page's loading functions won't allow me to reject controls individually.
Brian
A: 

There's two things at work here:

  1. Catching the error
  2. Swapping in an "error" control

Catching the error is pretty straightfoward. It comes down to try...catch around the code that could conceivably throw an error.

As for swapping in the error control (in the catch block), there's a couple ways to do it.

  1. You could have a hidden placeholder in your control that you just display that says, "there was an error." So, you're not removing the bad control, just replacing what it says.
  2. Each control has a "Parent" which has a "Controls" collection (which the current control will be part of). So, you could iterate the Parent.Controls collection to find the current control, then do "Parent.AddAt(index, myErrorControl)" to insert the error control, then remove the current control (or just set "Visible = false" on it).
Deane
Your proposal for #1 requires me add exception-handling to the usercontrol itself. This works and is in fact what my current program does. However, I'd be more interested in a way to do this without even touching the user control itself.
Brian
Hmmm. You could override CreateChildControls in the page, and wrap THAT in error handling. But I don't know a way to individually wrap a single control's creation, other than applying error handling directly to the control.
Deane