Unit testing 单元测试控制台输出
如果我正在测试与错误相关的内容,我可能希望最初在控制台中查看消息或堆栈跟踪。在我对测试感到满意之后,我通常不希望控制台被任何可能有助于快速发现和诊断失败测试的东西弄得乱七八糟。但在重构时,再次输出额外的信息有时是有用的。所以我有很多行分散在我评论/取消注释的地方,比如:Unit testing 单元测试控制台输出,unit-testing,debugging,trace,Unit Testing,Debugging,Trace,如果我正在测试与错误相关的内容,我可能希望最初在控制台中查看消息或堆栈跟踪。在我对测试感到满意之后,我通常不希望控制台被任何可能有助于快速发现和诊断失败测试的东西弄得乱七八糟。但在重构时,再次输出额外的信息有时是有用的。所以我有很多行分散在我评论/取消注释的地方,比如: // System.Diagnostics.Debug.WriteLine(msg); 什么是更干净的方法 干杯, 贝里尔 ==编辑 下面是一个例子,我的意思是,根据Josh的建议更新为使用日志服务 作为单元测试,我想断言将向
// System.Diagnostics.Debug.WriteLine(msg);
什么是更干净的方法
干杯,贝里尔 ==编辑 下面是一个例子,我的意思是,根据Josh的建议更新为使用日志服务 作为单元测试,我想断言将向用户显示一个错误,在这种情况下,因为新部门有一个重复的名称。我可以并且确实能够自动生成具有正确内容的消息 信息还必须通过一个基本的嗅觉测试,而这个测试是不能自动完成的——它是一个结构良好的句子,大多数用户都能很快理解并知道如何修复吗?我不想启动用户界面,让用户确保它不是完全愚蠢的,所以我想通过打印出来来吸引眼球。正如我前面提到的,这只是噪音,除了信息的几次变化
[Test]
public void WhenThePropertyIsChanged_IfDuplicateIsFound_DuplicateNameIsPartOfBrokenRuleMessage()
{
const string newName = "Blah";
// force a duplicate
_dao.Stub(x => x.FindByName(newName)).Return(new Department(newName));
var vm = _masterVm.Departments.Last();
vm.Name = newName;
var msg = vm.GetBrokenRules().First().Description;
Log.Service.WriteLine(msg); <=== print it
Assert.That(msg, Is.StringContaining(newName));
Assert.That(vm.BrokenRules.First().Description, Is.EqualTo(msg));
}
[测试]
更改属性时公共无效\u如果发现重复项\u重复项名称是BrokenruleMessage()的一部分
{
常量字符串newName=“Blah”;
//强迫复制
_Stub(x=>x.FindByName(newName)).Return(newdepartment(newName));
var vm=_masterVm.Departments.Last();
vm.Name=newName;
var msg=vm.getBrokerRules().First().Description;
Log.Service.WriteLine(msg);将您的日志语句包装到服务中,并向接口编码
public interface ILoggingService
{
void WriteLine(String msg);
}
创建一个静态类,该类允许访问日志记录服务,但允许您设置该服务
internal static class Log
{
private static ILoggingService _loggingService;
internal static ILoggingService Service
{
get{ return _loggingService ?? (_loggingService = new DefaultLoggingService()); }
set{ _loggingService = value; }
}
}
现在,您可以在只写入调试流的测试中实现服务
public class DebugLoggingService: ILoggingService
{
public void WriteLine(String msg)
{
System.Diagnostics.Debug.WriteLine(msg);
}
}
Log.Service = new DebugLoggingService();
您的代码现在可以保持不变,您只需通过注释那里的行来更改DebuggLoggingService。或者更好的是,您可以将其包装在\if DEBUG…\endif
语句中。最好使用控制台输出的断言。如果计算机可以显示它,它也可以验证它,速度比您快得多
如果您没有真正的单元测试,并且正在手动进行测试,您可以使用,这样您就可以轻松地调整所需的跟踪级别。没有断言的单元测试是不可能的;我要说的是微调类型的东西,有时候除了断言之外,它还很有用。@Berryl:同意,但不是每个人都在使用单元测试我也这么认为。在我看来,您可能没有编写自动单元测试,因此我的评论。
尽管如此,您通常不需要打印语句。您的代码或测试中是否有这些语句?测试中的语句将最终转换为断言。
不过,Log4j或任何建议仍然存在。@phillipe。请参阅原始帖子末尾的编辑,以了解打印的动机和一个示例测试用例。值得打印的单元测试的总百分比非常小。如果我很了解log4net,我可能会以某种方式使用它,但Josh的建议是对我之前所做的工作的明确升级。干杯!干杯!干杯!干杯!干杯不管怎么说,你在使用Log4Net,你还会实现该服务吗?还是Log4Net会实现该服务呢???@Berryl——我通常会将我的第三方内容粘在接口边界后面,这样我就不会得到“框架”锁定。我经常使用Entlib进行日志记录,但我仍然像上面那样使用服务边界。这样,如果我想用其他东西替换日志框架,我可以。