【发布时间】:2009-08-20 02:56:57
【问题描述】:
几天前,我看到 CoClassAttribute 以一种我以前从未想象过的方式使用。
[ComImport, CoClass(typeof(Foo)), Guid("787C1303-AE31-47a2-8E89-07C7257B1C43")]
interface IFoo {
void Bar();
}
class Foo : IFoo {
public void Bar() {
Console.WriteLine("Oh retado!");
}
}
被用作:
class CoClassDemo {
public static void Show() {
var a = new IFoo();
a.Bar();
}
}
这应该不会让我感到惊讶,因为 COM Interop 从 .NET Framework 的早期开始就是这样做的。在 .NET Reflector 中挖掘 COM 互操作代码时,我根本没有过多关注。
method public hidebysig static void Show() cil managed
{
.maxstack 1
.locals init (
[0] class ConsoleApplication1.IFoo a)
L_0000: nop
L_0001: newobj instance void ConsoleApplication1.Foo::.ctor()
L_0006: stloc.0
L_0007: ldloc.0
L_0008: callvirt instance void ConsoleApplication1.IFoo::Bar()
L_000d: nop
L_000e: ret
}
发生的事情是,在 COM Interop 的上下文之外,我立即设想它被用作穷人的编译时依赖注入。
所有要做的就是去掉接口名称上传统的“I”前缀(COM Interop 也是如此)。
然后就是更改 CoClass 属性以将一个实现换成另一个实现、模拟等。
我预先看到的两个缺点是必须重新编译(这几乎限制了测试场景的开发时间)以及当接口和实现部署到不同的程序集时围绕循环依赖的最终问题。
有人玩过这种技术吗? 还有什么缺点吗? 其他用途?
【问题讨论】:
-
高中时上过商店课吗? “为正确的工作使用正确的工具。”使用专为 COM 互操作设计的工具来做完全不同的事情是个坏主意。这使得下一个必须维护它的人无法理解你的代码。请记住,下一个人很可能是你,多年后你已经完全忘记了自己为什么会做这件疯狂的事。
标签: c# dependency-injection mocking