更具体地说:我想要一个单元测试来触发 SaveFileDialog 的FileOk事件,以测试我自己的代码(包装 SFD 并在 ShowDialog 之前和之后做一些额外的事情)是否按预期工作。
提前感谢您对此的任何帮助。
问题是,事件不会公开“引发”操作* - 它们公开“订阅”和“取消订阅”。他们如何实现订阅/取消订阅取决于实现。
但是,在SaveFileDialog
(或任何FileDialog
)的情况下,有一个OnFileOk
受保护的方法会引发事件。您可以派生SafeFileDialog
并公开一个将调用OnFileOk
或仅OnFileOk
使用反射调用的公共方法。然后它将调用事件处理程序FileOk
。我不确定我是否特别喜欢这些攻击计划中的任何一个,但如果没有更多关于你想要做什么的信息,我想我会回答这个问题而不是问太多:)
*
事实上,.NET 本身确实有事件“引发”部分的想法,因此EventInfo.GetRaiseMethod
. 但是,这违背了事件 IMO 的一般概念,并且 C# 编译器从不生成 raise 部分。我不相信标准库通常也不会公开它。
我相信可以使用PrivateObject在您的类上调用私有/受保护的方法。
如果您将 SaveFileDialog 隐藏在接口后面,则可以使用存根或模拟实现来测试您的代码。我不建议在单元测试中使用真实的表单或控件,因为它们中的大多数都严重依赖于活动的消息循环。
public interface ISaveFileDialog
{
event CancelEventHandler FileOk;
}
public class SaveFileDialogStub : ISaveFileDialog
{
public event CancelEventHandler FileOk;
public void RaiseFileOk(CancelEventArgs e)
{
FileOk(this, e);
}
}
public class ClassUnderTest
{
public ClassUnderTest(ISaveFileDialog dialog)
{
dialog.FileOk += OnFileOk;
}
void OnFileOk(object sender, CancelEventArgs e)
{
//...
}
}