当我在开发一个按需将程序集安装到 GAC 的应用程序(单击按钮时)并尝试在单击下一个按钮或尝试从那个新的 GAC-ed 程序集,但失败了。问题和重现步骤如下。
问题和重现步骤: 创建一个类似于以下的新类库,命名为 FooGreet.dll 并将其命名为强名称。稍后我们将它拖到程序集文件夹中。
namespace FooGreet
{
public class Greeting
{
public string SayHello()
{
return "Hello";
}
}
}
创建一个控制台应用程序来加载上面的类库,类似于下面的代码。
namespace FooGreetCaller
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Press Enter to load assembly..");
while (true)
{
string input = Console.ReadLine();
if (input == "q" || input == "Q")
break;
try
{
System.Reflection.Assembly.Load("FooGreet, Version=1.0.0.0, Culture=Neutral, PublicKeyToken=3f330bcf59df56c9");
Console.WriteLine("Assembly load success.");
}
catch (Exception eX)
{
Console.WriteLine(eX.Message + Environment.NewLine + eX.StackTrace);
}
}
}
}
}
- 运行控制台应用程序: 运行控制台应用程序的一个实例。尝试加载 FooGreet.dll,无论加载多少次,都会出现“无法加载文件或程序集……”的异常。不要关闭控制台窗口。
- 将 FooGreet.dll 安装到 GAC: 将 FooGreet.dll 拖到 GAC,在控制台应用程序的同一个实例上,尝试再次加载 FooGreet.dll,仍然出现相同的异常;我称之为异常,因为 FooGreet.dll 在 GAC 中,并且控制台应用程序应该已经识别它。不应该吗?
- 运行控制台应用程序的第二个实例: 运行控制台应用程序的第二个实例。尝试加载 FooGreet.dll,现在程序集加载正常。
- 从 GAC 卸载 FooGreet.dll: 转到 GAC,卸载 FooGreet.dll。尝试在控制台应用程序的第二个实例中再次加载 FooGreet.dll。程序集已成功加载。理想情况下,它不应该抛出“无法加载文件或程序集......”之类的异常吗?
问题: 问题在第 2 步和第 4 步。从第 2 步和第 4 步的情况来看,看起来当应用程序加载时,它会拍摄 GAC 的快照(至少使用默认的 AppDomain,我没有尝试创建并加载一个新的 AppDomain)。这是真的?
(在我的应用程序中,作为一种解决方法,我在将特定程序集注册到 GAC 后重新启动应用程序
System.EnterpriseServices.Internal.Publish().GacInstall(targetAssemblyName);
我在一个 WinForms 应用程序上,我正在 Form_Load 中重新启动,这会导致主窗体闪烁几分之一秒......我不喜欢)