如何拦截调用:在.NET /到thirdy党库非虚方法?(How to intercept a ca

2019-07-30 17:52发布

我想,我需要的是什么。净人称之为“透明动态代理”,但我已经看到了这个的实现远(城堡DynamicProxy,Spring.NET AOP等)需要我做的这些至少一个:

  1. 声明截获方法如虚拟
  2. 包装类并创建封装类包装的实例,而不是
  3. 更改继承或实现接口

显然,如果两个主叫方和被叫方都是非虚和thirdy方封闭源代码库,是哪种情况,有什么我能做的。

如果C#都像Python这样的动态语言,我会做这样的事情:

foo = ThirdyPartyLibA.Foo()
def interceptor(self, *args, **kwargs):
    do_something_before(self, *args, **kwargs)
    result = ThirdyPartyLibB.Bar.intercepted(self, *args, **kwargs)
    do_something_after(self, result, *args, **kwargs)
    return result
foo.bar.intercepted = interceptor # bar is an instance of ThirdyPartyLibB.Bar
foo.do_its_job() # Foo.do_its_job calls Bar.intercepted

我需要这个改变ThirdyPartyLibA.Foo的不良行为,而与ThirdyPartyLibB.Bar交互。 我知道到底是什么原因导致这种行为,究竟是如何改变富或酒吧来修复这个bug感谢dissasemblers。

一些(很可能无法工作)的想法:

  • 拆开ThirdyPartyLibA,使代码的更改并生成一个兼容的组件(不大可能奏效,因为它是一个强命名程序集)
  • 编辑二进制使Foo的马车方法虚拟和改变一切必要为它仍然是一个有效的汇编,所以我可以使用动态代理(不太可能的工作,也因为同样的原因为理念以上)
  • 找到适合透明的动态代理实现(我觉得这是在此基础上论坛主题无: http://www.pcreview.co.uk/forums/overriding-non-virtual-methods-using-il-and-reflection-发射-t2605695.html )
  • 联系创建该库公司(他们不支持的产品了)
  • 停止使用该库或使用其它的(不可能的,因为它是一个RAD IDE,我们是绑因为没有书面使用IDE自己的语言的代码量巨大的运行时的一部分)
  • 控制权问题的方法的调用,以避免故障(我们已经做到这一点,但它并没有完全解决问题)

你有什么其他的想法?

PS:对不起,我的英语不好。 此外,对不起我的Python。 此代码是在这里只是为了说明我需要什么,不要把它作为一个药方,因为那太可怕了。

Answer 1:

可能的解决方案1:

包库和使用像ReSharper的一个工具,以找到库的所有用途,并与包装类代替。 你也可以利用这个机会清理第三方库的大概是蹩脚的界面。

可能的解决方案2:

虽然TypeMock一般用来作为测试工具,它可以让你嘲笑一切。 因为它注入本身作为一个代码分析器,东西你可以模拟包括类私有和静态成员。 作为奖励,任何重载方法不必是虚拟的,所以你可以拦截来电的方式。

我的建议

我建议你与解决方案1.去一个包装是很容易理解的,这会给你真正提高代码的好机会。 我甚至建议你换第三方库作为一般规则。



Answer 2:

如果酒吧是静态的,你也许能够使用痣迂回的方法调用。 请注意,这是一个非常严厉的方法来修复该错误,并且真的不建议在生产代码,但如果你绝望它是一个选项。



文章来源: How to intercept a call to a nonvirtual method from/to thirdy-party libraries in .Net?