我接管了一个使用WCF服务的项目。代码有一些“代码味道”,我想重构这些气味,我需要有关如何重构代码重复气味的建议。 WCF服务调用的每个方法都如下所示:
public Result MyMethod(string aString, string bString)
{
string methodName = MethodBase.GetCurrentMethod().Name;
using (LogService log = LogFactory.Create())
{
try
{
<stmts>
log.Info(methodName, "Created entity xyz");
<stmts>
}
catch (Exception ex)
{
log.Error(methodName, ex.message);
}
}
}
问题是如何重构此代码?每个WCF调用都使用此“代码模板”。
答案 0 :(得分:4)
您可以使用之前和之后的操作调用以下内容:
private static void ActionWithLog(Action before, Action after)
{
string methodName = MethodBase.GetCurrentMethod().Name;
using (LogService log = LogFactory.Create())
{
try
{
before();
log.Info(methodName, "Created entity xyz");
after();
}
catch (Exception ex)
{
log.Error(methodName, ex.message);
}
}
}
例如:
ActionWithLog(() => service.Operation1(), () => service.Operation2());
答案 1 :(得分:2)
关于例外的一个好处是,如果他们没有被抓住,他们就会冒泡。因此,让他们达到一个级别(或几个),在一个更大的尝试捕获和日志记录将有所帮助。 异常的.stacktrace属性将包含方法名称,并且记录它而不仅仅是消息和方法名称可能非常方便,因此您不会丢失该信息。
答案 2 :(得分:2)
您可以将此代码作为方法并调用它,将内部代码作为委托或Action / lambda表达式传递:
public Result MyMethod(string aString, string bString, MyDelegate a, MyDelegate b)
{
string methodName = MethodBase.GetCurrentMethod().Name;
using (LogService log = LogFactory.Create())
{
try
{
a();
log.Info(methodName, "Created entity xyz");
b();
}
catch (Exception ex)
{
log.Error(methodName, ex.message);
}
}
}
然后称之为:
MyMethod("foo", "bar", delegate{/*your code goes here*/}, delegate{/*your code goes here*/});
如果您不喜欢内联代理,请使用以下单独的方法创建代理:
MyMethod("foo", "bar", new MyDelegate(myMethodA), new MyDelegate(myMethodB));
答案 3 :(得分:0)
它是横切功能,如:日志记录,异常处理等。 您可以使用AOP来消除它。否则我不建议你重构这段代码。 这是一个很好的.NET AOP框架:http://www.sharpcrafters.com/但它不是免费的:)。您可能想要搜索免费的。