我正在动态加载用户控件,将它们添加到Web窗体的Controls集合中。
我想隐藏用户控件,如果它们在渲染时导致未处理的异常。
因此,我尝试 Hook 到每个UserControl的Error事件,但似乎该事件从未像对Page类一样对UserControls触发。
进行了一些谷歌搜索,似乎没有希望。这里有什么想法吗?
最佳答案
mmilic,从your response到我的previous idea ..
无需其他逻辑!重点是,您对所涉及的类不执行任何操作,只需将它们包装在一些实例化泡沫包装中即可! :)
好的,我只是想提出要点,但我想亲自看看这项工作,因此我将一些非常粗糙的代码拼凑在一起,但是这个概念确实存在并且似乎可行。
长期职位的歉意
安全加载器
这基本上就是我提到的“气泡”。它将获取控件HTML,捕获在渲染过程中发生的任何错误。
public class SafeLoader
{
public static string LoadControl(Control ctl)
{
// In terms of what we could do here, its down
// to you, I will just return some basic HTML saying
// I screwed up.
try
{
// Get the Controls HTML (which may throw)
// And store it in our own writer away from the
// actual Live page.
StringWriter writer = new StringWriter();
HtmlTextWriter htmlWriter = new HtmlTextWriter(writer);
ctl.RenderControl(htmlWriter);
return writer.GetStringBuilder().ToString();
}
catch (Exception)
{
string ctlType = ctl.GetType().Name;
return "<span style=\"color: red; font-weight:bold; font-size: smaller;\">" +
"Rob + Controls = FAIL (" +
ctlType + " rendering failed) Sad face :(</span>";
}
}
}
和一些控件
好的,我只是在这里 mock 了两个控件,一个控件将抛出另一个控件将渲染为垃圾。指向这里,我不要胡扯。这些将替换为您的自定义控件。
不良控制
public class BadControl : WebControl
{
protected override void Render(HtmlTextWriter writer)
{
throw new ApplicationException("Rob can't program controls");
}
}
良好控制
public class GoodControl : WebControl
{
protected override void Render(HtmlTextWriter writer)
{
writer.Write("<b>Holy crap this control works</b>");
}
}
这页纸
好的,让我们看一下“测试”页面。在这里,我只是实例化控件,获取它们的html并输出它,然后我将介绍有关设计人员支持的想法。
页面代码隐藏
protected void Page_Load(object sender, EventArgs e)
{
// Create some controls (BadControl will throw)
string goodHtml = SafeLoader.LoadControl(new BadControl());
Response.Write(goodHtml);
string badHtml = SafeLoader.LoadControl(new GoodControl());
Response.Write(badHtml);
}
思想
好的,我知道您在想什么,“这些控件以编程方式实例化,那么对设计师的支持又如何呢?我花了很多时间才使这些控件对设计师来说很好,现在您正在弄乱我的mojo”。
好的,所以我还没有真正测试过它(可能会在一分钟内完成!),但是这里的想法是覆盖页面的CreateChildControls方法,并获取表单上添加的每个控件的实例,并通过SafeLoader运行它。如果代码通过,则可以按正常方式将其添加到Controls集合中,如果没有通过,则可以创建错误的文字或其他内容,由我的 friend 决定。
最后..
再次,对冗长的帖子表示抱歉,但我想在此处获取代码,以便我们进行讨论:)
我希望这有助于证明我的想法:)
更新
通过将控件插入设计器中并使用此方法覆盖CreateChildControls方法进行测试,效果很好,可能需要进行一些清理才能使外观看起来更好,但我将留给您;)
protected override void CreateChildControls()
{
// Pass each control through the Loader to check
// its not lame
foreach (Control ctl in Controls)
{
string s = SafeLoader.LoadControl(ctl);
// If its bad, smack it downnnn!
if (s == string.Empty)
{
ctl.Visible = false; // Prevent Rendering
string ctlType = ctl.GetType().Name;
Response.Write("<b>Problem Occurred Rendering " +
ctlType + " '" + ctl.ID + "'.</b>");
}
}
}
享受!
关于asp.net - 捕获ASP.NET UserControls中未处理的异常,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/10793/