InternalsVisibleTo 用于动态生成程序集,但具有强命名

Dan*_*ant 4 c# strongname reflection.emit dynamic internalsvisibleto

我有一个使用动态代码生成来创建代理类的项目。该代理类利用项目的内部类(以便不暴露实现细节),因此我将InternalsVisibleTo 与动态生成的程序集的名称一起使用。直到最近,当我的客户强行要求所有交付的程序集都必须是强名称时,这种方法一直运行良好。

出现此问题的原因是,为了将 InternalsVisibleTo 与强名称程序集一起使用,它引用的程序集也必须是强名称的,并且您必须提供公钥。我遇到困难的是如何为动态生成的程序集提供强名称。这是我到目前为止所做的:

  1. 我为动态程序集创建了一个新的密钥对,以便 .snk 可以随产品一起提供(显然我们不想提供用于签署其余项目程序集的 .snk。)
  2. 我已经提取了 PublicKey 并更新了 InternalsVisibleTo,以将新的动态 PublicKey 用于动态引用的程序集。
  3. 我尝试对动态生成的程序集进行签名,如下所示:

        var name = new AssemblyName("ProxyBuilderAssembly");
        var attributes = new CustomAttributeBuilder[1];
        attributes[0] =
            new CustomAttributeBuilder(typeof(AssemblyKeyFileAttribute).GetConstructor(new[] {typeof(string)}),
                                       new object[] {"Dynamic.snk"});
        _assembly = AppDomain.CurrentDomain.DefineDynamicAssembly(name, AssemblyBuilderAccess.RunAndSave, attributes);
        _module = _assembly.DefineDynamicModule("ProxyBuilderAssembly", "ProxyBuilderAssembly.dll");
    
    Run Code Online (Sandbox Code Playgroud)

不幸的是,这不起作用,我一直很难找到任何关于它如何工作的文档。有谁知道如何对动态生成的程序集进行签名,以便可以通过InternalsVisibleTo 对其进行访问?我可以将必要的类公开,但这最终会泄漏实现细节,而这些细节最好还是封装起来。

R. *_*des 5

MSDN 上有一篇“ How to: Use Full Signing to Give a Dynamic Assembly a Strong Name ”文章,展示了如何对使用 Reflection.Emit 生成的程序集进行签名。

StrongNameKeyPair kp;
// Getting this from a resource would be a good idea.
using(stream = GetStreamForKeyPair())
{
    kp = new StrongNameKeyPair(fs);
}
AssemblyName an = new AssemblyName();
an.KeyPair = kp;
AssemblyBuilder ab = AppDomain.CurrentDomain.DefineDynamicAssembly(an, AssemblyBuilderAccess.RunAndSave);
Run Code Online (Sandbox Code Playgroud)