PoSh cmdlet的程序集解析导致其他模块导入失败

时间:2015-03-26 18:29:03

标签: c# powershell .net-assembly assembly-resolution

我有一个用C#编写的PowerShell模块。由于该模块使用了Google API,我需要引用一个特定的 System.Net.Http.Primitives.dll 。在C#中运行代码没有加载该模块的问题,但是在PowerShell中我必须指定要加载的程序集,否则会抛出错误,指出无法找到程序集。

也就是说,我的Cmdlet类继承自IModuleAssemblyInitializer并按照建议OnImport实现here方法。底层的C#代码如下所示:

public void OnImport() {
    AppDomain.CurrentDomain.AssemblyResolve += ResolveSystemPrimitives;
}

private static Assembly ResolveSystemPrimitives(object sender, ResolveEventArgs args) {
    Assembly accurate = Assembly.LoadFrom(System.IO.Path.Combine(AssemblyDirectory,
        "System.Net.Http.Primitives.dll"));
    return accurate;
}

直到最近有人报告如果他们先加载我的模块然后尝试加载另一个模块,这一直有效,他们会遇到一系列错误。例如,如果您尝试在PowerShell中加载Active Directory模块:

PS C:\> Import-Module ActiveDirectory

Import-Module : The following error occurred while loading the extended type data file: 
, C:\Windows\system32\WindowsPowerShell\v1.0\Modules\ActiveDirectory\ActiveDirectory.Types.ps1xml(11) : Error in type "Microsoft.ActiveDirectory.Management.ADEntity": Exception: Cannot convert the 
"Microsoft.ActiveDirectory.Management.ADEntityAdapter" value of type "System.String" to type "System.Type".
...A lot more of these

但是,如果重新打开PowerShell并以相反的顺序加载模块,则没有问题。到目前为止,我发现的所有错误都与我加载Primitives程序集有关 - 如果我发表评论,我的代码会失败,但模块都可以正常加载。

为了使事情进一步复杂化,我尝试使AssemblyResolve处理程序具有选择性,这样它只会在它正在寻找的时候加载Primitives.dll。但是,当我在事件处理程序ResolveSystemPrimitives上向check the ResolveEventArgs.Name property抛出一个断点时,它只被触发两次,而且两个值都不是Primitives库,而是 Microsoft.PowerShell.Commands.Management System.Management.Automation.resources

那么,如何更新我的程序集解析代码以防止它进一步破坏PowerShell模块导入?在测试时,这在Windows 7和8.1上是一个问题,并使用.Net 4.0目标版本。

更新 - 当我正在处理这组Cmdlet时,另一个问题出现在我的 Microsoft.Powershell.Management 模块将完全从Powershell中丢失,以及所有它提供的基本Cmdlet。起初我以为这是由于我的模块,但即使没有引用它,事情也会出错。

经过几次重新启动和几次调用Import-Module Microsoft.Powershell.Management以提醒PoSh它需要组装后,事情又开始起作用了。然后一切都开始了。我似乎根本没有上述问题 - 我可以按任何顺序加载模块而不会产生反响,而我的AssemblyResolve处理程序实际上看到了正确的程序集错误。

我不知道发生了什么。

0 个答案:

没有答案