【问题标题】:How can I force an application to load .NET classes from a different assembly?如何强制应用程序从不同的程序集中加载 .NET 类?
【发布时间】:2013-10-12 02:14:18
【问题描述】:

有没有人知道有什么方法可以强制应用程序从单独的文件中加载特定的 .NET 类,而不需要该应用程序的源代码?比如说,如果我想对 mscorlib 中的单个类进行更改并查看某个应用程序中发生了什么,我不想为 每个单个类创建一个包装 DLL mscorlib。让我想到这一点的一件事是因为我绝对讨厌 Windows 文件夹浏览器对话框,并且我希望能够为 FolderBrowserDialog 编写一个替换类。然后,每当应用程序尝试使用它时,它都会使用我的。

我刚刚找到TypeForwardedToAttribute,但这需要访问源代码。我希望能够对我没有任何源代码的现有应用程序执行此操作。

【问题讨论】:

    标签: c# .net class redirect


    【解决方案1】:

    Assembly redirection / publisher policy 用于此目的,但您不太可能将其应用于 mscorlib,尤其是在系统范围内。使用程序集重定向时,可以将给定程序集重定向到同一程序集的不同版本,但目标程序集必须具有与原始程序集相同的公钥令牌。由于 mscorlib 被强命名(在 GAC 中),因此您不太可能在修改后重新签名。

    另外,请记住 FolderBrowserDialog 内部使用 SHBrowseForFolder 因此,如果您设法重定向它或重定向 mscorlib,您仍然只处理托管应用程序 - 任何本机应用程序仍将使用底层 SHBrowseForFolder 调用并且您'最终会在不同的应用程序中看到不同的文件夹对话框。

    另外(在阅读您的评论后)您的用户可能已经熟悉“常规”Browse for folder 对话框 - 如果您这样做,给他们一个不同的对话框可能最终会使他们中的一些人感到困惑。我并不是说这是一个很棒的对话框(它不是),但所有应用程序的标准行为对于用户来说比具有更好对话框的单个应用程序更好。

    为什么不在您自己的项目中创建一个新的文件夹浏览器对话框呢?这样做并不难。这里有一个 article 开头 - 它包含其他文章的链接,这些文章描述了更改对话框的技术(但仅限于单个应用程序中)。

    【讨论】:

    • 显然我不会在自己的应用程序中使用FolderBrowserDialog;我更尊重我的用户。 ;-) 无论如何,这只是一个例子。但是,我不是在谈论我编写的软件。我说的是在不访问其源代码的情况下修改现有应用程序的行为。
    • @flarn2006 我编辑了关于 SHBrowseForFolder 的答案,这是 .NET 包装器使用的底层 API。
    【解决方案2】:

    可能使用 .Net 策略设置。检查 this (摘自 Don Box 的优秀 Essential .Net)。尤其是代码清单 2.4 和图 2.11。唯一的问题是我不确定您是否可以使用这种技术覆盖内置的 .Net 类和程序集。

    清单 2.4。设置版本政策

    可以在三个级别指定版本策略:每个应用程序、每个组件和每个机器。这些级别中的每一个都有机会处理版本号,其中一个级别的结果作为其下一级的输入。如图 2.11 所示。请注意,如果应用程序和机器的配置文件都具有给定程序集的版本策略,则首先运行应用程序的策略,然后通过机器范围的策略运行生成的版本号以获取用于定位的实际版本号大会。在此示例中,如果机器范围的配置文件将 Acme.HealthCare 的 1.3.0.0 版本重定向到 2.0.0.0 版本,则程序集解析器将在请求版本 1.2.3.4 时使用版本 2.0.0.0,因为应用程序的版本策略映射版本 1.2 .3.4 到 1.3.0.0。

    【讨论】:

    • 是的,但我说的是类级重定向。您所指的不是一次仅适用于整个程序集吗?我仍然希望它正常使用该程序集,但我希望从其他地方加载的一两个类除外。
    • 是的,但是如果您编写一个替代程序集,该程序集将重定向到每个类的内置程序集,除了您要覆盖...的行为的类之外,我并不是说这会很聪明,实际上它可能在很多方面都非常不聪明,但你在问它是否可能......
    • 是的,但是必须为每个类和每个方法都放置一个存根仍然很痛苦,尤其是在更新时。是否有某种工具可以将程序集分解成类似于 jar 文件的东西,这样我就可以替换单个类并将它们打包在一起?
    【解决方案3】:

    您可以随时尝试使用ILSpy 反编译 dll。它允许您从任何 .net dll 中生成包含生成源代码的项目文件。

    然后您可以编辑生成的源代码并编译修改后的 dll。

    【讨论】:

    • 好主意,但反编译并不总是完美的,如果我只想更改一些类,我宁愿不必为一大堆类处理不完美的反编译。
    • 你可以简单的输出你需要的类。您不必为整个 dll 输出代码。只需获取您需要的代码,它应该没问题(在您不需要包含的类中会有一些代码)。为了实现其他平台在其 SDK 中没有的功能,我必须进行大量反编译,而且我没有遇到任何问题。
    • 但是我怎样才能让它为我没有替换的类使用原始 DLL?
    • 实际上,您实际上会反编译并输出要更改的应用程序的源代码,然后打开生成的项目文件。然后将新类添加到项目中,并简单地使用新类而不是 mscorlib 类。然后,您将能够编译并运行修改后的应用程序。
    猜你喜欢
    • 2010-11-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多