7

我正在考虑在我的应用程序上实现一个简单的崩溃报告,该报告会询问用户是否愿意将崩溃日志发送给我们。

我以前从未做过崩溃报告,我习惯做的是尝试/捕获将错误保存到日志文件。

  1. 实施崩溃报告系统的正确方法是什么?

  2. 当应用程序崩溃或发送数据的正确方法是什么时,如何触发崩溃报告以打开并发送转储?

我认为以上是我对它如何工作或应该如何工作的最大疑问......我不完全确定崩溃报告是否会是 try/catchs 与在上述情况发生时触发的外部应用程序的交互,或者会是什么遵循它的正确方法。

我没有可用的 SQL Server,所以我打算使用一个简单的上传脚本,报告转储的应用程序将使用它来发送数据。

请原谅我对崩溃报告的工作原理一无所知,我希望社区可以帮助我更好地理解它。

我正在四处搜索崩溃报告,发现大多数事情都围绕着 Crystal Report,准备去库等,但我想从小处着手,以便在深入研究一些大型库或其他解决方案之前更好地理解它在我这边可用。

4

4 回答 4

5

您是否考虑过使用内置的Windows 错误报告

您可以使用 Winqual 网站查看与您的组织相关的特定于驱动程序、特定于应用程序或特定于操作系统的错误。每个错误报告都提供与该存储桶相关的详细信息,然后您可以请求相关数据的文件。

查看错误报告:

  1. 建立一个 Winqual 帐户。为了保护公司免受假冒并确保错误报告发送给正确公司的代表,Winqual 网站要求您的公司拥有有效的 VeriSign ID。

• 请咨询您的法律部门;您的公司可能已经拥有 VeriSign ID(也称为软件发行商的 Authenticode 数字 ID)。• 检查Winqual 以查看您的公司是否已经有一个帐户。

  1. 接受 Windows 错误报告协议。

  2. 登录 Winqual 网站。

  3. 单击 Windows 错误报告。

这篇旧文章可能会感兴趣:A Simple Class to Catch Unhandled Exceptions in WinForms

于 2010-12-12T06:48:48.427 回答
4

很大程度上取决于应用程序和(特别是)用户的预期隐私问题。

假设这是一个运行在用户 PC 上的客户端应用程序,如果这是一个“内部网”内部应用程序,那么在应用程序退出时让应用程序通过电子邮件将日志文件发送给您应该非常简单。

这可能很有趣,因为有时您会在用户开始报告之前修复错误。

或者,如果您担心应用程序可能会崩溃并且无法正确捕获未处理的异常,您可以

  1. 在启动时,写一个注册表项(或虚拟文件项,或你有什么)标记“应用程序未正确终止”
  2. 在干净的出口上,清理注册表项(或你有什么)
  3. 启动时,检查注册表项(等)是否存在。

如果标记存在,那么您知道应用程序以不干净的方式崩溃,因此您可以使用文本提示用户,例如“上次运行此程序时它似乎没有正确退出。您想发送一个记录发生在我们身上的事情,以便我们尝试解决可能发生的任何问题?”

于 2010-12-12T07:44:52.437 回答
4

滚动您自己的异常处理程序。在您的 program.cs 类中使用以下代码。发生异常时会自动发送邮件。

using System;
using System.Windows.Forms;
using System.Net;
using System.Net.Mail;
using System.Threading; 

namespace ExceptionHandlerTest
{
    static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            Application.ThreadException +=
                new ThreadExceptionEventHandler(Application_ThreadException);

            // Your designer generated commands.
        }

        static void Application_ThreadException(object sender, ThreadExceptionEventArgs e) 
        {

            var fromAddress = new MailAddress("your Gmail address", "Your name");
            var toAddress = new MailAddress("email address where you want to receive reports", "Your name");
            const string fromPassword = "your password";
            const string subject = "exception report";
            Exception exception = e.Exception;
            string body = exception.Message + "\n" + exception.Data + "\n" + exception.StackTrace + "\n" + exception.Source;

            var smtp = new SmtpClient
            {
                Host = "smtp.gmail.com",
                Port = 587,
                EnableSsl = true,
                DeliveryMethod = SmtpDeliveryMethod.Network,
                UseDefaultCredentials = false,
                Credentials = new NetworkCredential(fromAddress.Address, fromPassword)
            };
            using (var message = new MailMessage(fromAddress, toAddress)
            {
                Subject = subject,
                Body = body
            })
            {
                //You can also use SendAsync method instead of Send so your application begin invoking instead of waiting for send mail to complete. SendAsync(MailMessage, Object) :- Sends the specified e-mail message to an SMTP server for delivery. This method does not block the calling thread and allows the caller to pass an object to the method that is invoked when the operation completes. 
                smtp.Send(message);
            }
        }
    }
}

您可以通过从https://crashreporterdotnet.codeplex.com获取基于此的崩溃报告库来节省您的时间

于 2012-05-15T09:29:36.773 回答
1

尝试使用 AppDomain.UnHandledException 和/或 AppDomain.ThreadException

于 2010-12-12T06:47:22.927 回答