WPF处理丢失的dll

时间:2012-11-27 14:31:54

标签: wpf .net-4.0

我注意到在某些情况下,我没有分发应用程序所需的特定dll,应用程序不会提供任何错误,它只是不加载(在屏幕上显示)。它表现得像你还没有开始它。

有谁知道为什么会这样?

编辑:重现的步骤:

  1. 使用WPF应用程序项目和类库项目(ReferenceDll)创建解决方案。
  2. 将WPF应用程序项目中的引用添加到类库项目中。
  3. 在类库中,将此方法添加到Class1

    public int Calculate(int a,int b) {     返回a + b; }

  4. 将此代码放在App.OnStartup中:

    try
    {
        int result = new ReferenceDll.Class1().Calculate(2, 4);
    }
    catch (Exception ex)
    {
        File.WriteAllText(@"D:\Test\error.txt", ex.ToString());
    }
    
  5. 构建解决方案,然后从bin文件夹中删除ReferenceDll。运行该应用程序。

  6. 不会创建任何文件,app也不会显示。即使您在主视图中移动Try catch代码,在某些按钮单击事件中,Catch {}也永远不会被触发,它将显示无信息的消息

    AppName has stopped working.
    

    并提供调试选项,这对最终用户没用。

2 个答案:

答案 0 :(得分:1)

如果您没有任何Trace.WriteLine语句,那么我建议您添加一些。添加一些到异常处理程序。此外,您可以使用以下免费工具捕获跟踪并尝试以此方式缩小范围。

http://technet.microsoft.com/en-us/sysinternals/bb896647.aspx

您还可以覆盖app.xaml.cs中的Onstartup方法,并从那里实例化您的应用程序,并捕获任何异常和输出以进行跟踪。

<强>更新

我已尝试过您在更新中指明的步骤,并且加载的应用程序没有任何问题。我建议的下一件事是检查您部署到的环境中的.net框架的版本。如果您需要帮助,请查看此链接:

http://msdn.microsoft.com/en-us/kb/kbarticle.aspx?id=318785

<强>更新

将错误记录放在处理程序中,就像问题答案中的处理程序一样,您将看到错误。刚用你的例子尝试了这个并且它有效。错误告诉您到底出了什么问题:

System.IO.FileNotFoundException:无法加载文件或程序集“ReferenceDll,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null”或其依赖项之一。该系统找不到指定的文件。 文件名:'ReferenceDll,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null'    在WPFApp.App.OnStartup(StartupEventArgs e)    在System.Windows.Application。&lt; .ctor&gt; b__1(对象未使用)    在System.Windows.Threading.ExceptionWrapper.InternalRealCall(委托回调,对象args,Int32 numArgs)    在MS.Internal.Threading.ExceptionFilterHelper.TryCatchWhen(Object source,Delegate方法,Object args,Int32 numArgs,Delegate catchHandler)

警告:装配绑定日志记录已关闭。 要启用程序集绑定失败日志记录,请将注册表值[HKLM \ Software \ Microsoft \ Fusion!EnableLog](DWORD)设置为1。 注意:程序集绑定失败日志记录会导致一些性能损失。 要关闭此功能,请删除注册表值[HKLM \ Software \ Microsoft \ Fusion!EnableLog

WPF window crashes on startup, or it starts but hangs and does not render contents

答案 1 :(得分:1)

在辅助线程上抛出异常时可能会发生这种情况。请参阅this page上的备注部分:

  

独立或浏览器托管的WPF应用程序使用Application类来检测未处理的异常(请参阅DispatcherUnhandledException)。但是,Application只能检测在运行Application类的同一线程上抛出的未处理异常。通常,应用程序将具有一个主用户界面(UI)线程,因此Application类的未处理异常检测行为就足够了。但是,主UI线程上的Application类不会自动检测到辅助线程上抛出的未处理异常。

您可以尝试使用此事件来 catch 检测异常并记录错误: AppDomain.UnhandledException Event

AppDomain currentDomain = AppDomain.CurrentDomain;
currentDomain.UnhandledException += new UnhandledExceptionEventHandler(MyHandler);

static void MyHandler(object sender, UnhandledExceptionEventArgs args) {
   Exception e = (Exception) args.ExceptionObject;
   Console.WriteLine("MyHandler caught : " + e.Message);
}

UPDATE:

除了线程问题之外,如果你将try ... catch块放到错误的位置,它也可能是原因造成的。考虑这个例子:

public partial class App : Application
{
    protected override void OnStartup(StartupEventArgs e)
    {
        base.OnStartup(e);

        Do();

    }

    private void Do()
    {
        try
        {
            int result = new ClassLibrary1.Class1().Calculate(2, 4);
        }
        catch (System.Exception ex)
        {
            Console.WriteLine("MyHandler caught by try...catch: " + ex.Message);
        }
    }
}

这将导致调用Do()的行发生异常,因为CLR此处尝试解析程序集。未捕获异常并且应用程序终止。

但如果你试试这个:

public partial class App : Application
{
    protected override void OnStartup(StartupEventArgs e)
    {
        base.OnStartup(e);

        try
        {
            Do();
        }
        catch (System.Exception ex)
        {
            Console.WriteLine("MyHandler caught by try...catch: " + ex.Message);
        }
    }

    private void Do()
    {
        int result = new ClassLibrary1.Class1().Calculate(2, 4);
    }
}

输出结果为:

  

myHandler被try ... catch:无法加载文件或程序集'ClassLibrary1,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null'或其依赖项之一。系统找不到指定的文件。

请注意,在引用程序集的同一函数中订阅它时,不会触发UnhandledException事件。这也有效:

    protected override void OnStartup(StartupEventArgs e)
    {
        base.OnStartup(e);

        AppDomain currentDomain = AppDomain.CurrentDomain;
        currentDomain.UnhandledException += new UnhandledExceptionEventHandler(
            (sender, args) =>
            {
                Exception ex = (Exception)args.ExceptionObject;
                Console.WriteLine("MyHandler caught by UnhandledException handler: " + ex.Message);
            });

        Do();
    }

    private void Do()
    {
        int result = new ClassLibrary1.Class1().Calculate(2, 4);
    }

结果:

  

MyHandler被UnhandledException处理程序捕获:无法加载文件或程序集“ClassLibrary1,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null”或其依赖项之一。系统找不到指定的文件。

希望它有所帮助。