【问题标题】:Handle exception on service startup服务启动时处理异常
【发布时间】:2010-09-14 14:22:25
【问题描述】:

我正在编写一系列 Windows 服务。如果在启动期间抛出错误(在OnStart() 方法中),我希望它们失败。我原以为仅仅在OnStart() 中抛出一个错误就可以做到这一点,但我发现它反而“开始”并向我显示一条消息,指出“服务已启动,但处于非活动状态。这是正确的吗?” (释义)。我该如何处理错误,使其实际上无法启动服务?

【问题讨论】:

    标签: c# .net windows-services error-handling


    【解决方案1】:

    将所有启动逻辑移至单独的方法,并从该单独的方法中引发异常(或调用 OnStop)。

    OnStart 在启动时有些奇怪。我发现如果 OnStart() 中的行不超过一行,那么我不会收到“服务已启动然后停止。某些服务如果无工作可自动停止”消息,并且抛出的异常将终止处理并记录到应用程序事件日志。

    同样使用单独的启动方法,您可以使用这样的技术在不附加的情况下对其进行调试。 http://www.codeproject.com/KB/dotnet/DebugWinServices.aspx

    【讨论】:

      【解决方案2】:

      如果您运行的是 .NET 2.0 或更高版本,您可以使用 ServiceBase.Stop 从 OnStart 停止服务。否则从新线程调用 Stop。

      参考 [devnewsgroups] (http://www.devnewsgroups.net/group/microsoft.public.dotnet.framework/topic50404.aspx)

      (新闻组消失)

      【讨论】:

      【解决方案3】:

      如果您想要的主要内容是让“服务”窗口报告有错误,从我尝试过的(Windows 7 上的 .NET3.5)开始,唯一的方法是设置 @987654322 @。我建议将其设置为 13816,因为这会导致消息“发生未知错误”。见the windows error codes

      下面的示例完成了三件事。

      1. 设置 ExitCode 会为最终用户生成有用的消息。它不会影响 Windows 应用程序日志,但会在系统日志中包含一条消息。
      2. 调用 Stop 会导致应用程序日志中出现“服务已成功停止”消息。

      3. 抛出异常会在应用程序日志中生成有用的日志条目。

      protected override void OnStart(string[] args) {
          try {
              // Start your service
          }catch (Exception ex) {
              // Log exception
              this.ExitCode = 13816;
              this.Stop();
              throw;
          }  
      }
      

      【讨论】:

      • 13816 被标记为 IPSEC 错误,因此它并不完全适用,但服务控制管理器将任何非零 int 视为错误。我相信代码的含义取决于服务本身。
      • 这是一个很好的观点。也许,代码 1064 会更好。 (ERROR_EXCEPTION_IN_SERVICE - 处理控制请求时服务中发生异常。)对我来说,主要想法是向用户显示一条有帮助的消息,尤其是不会误导。
      • 关键部分是设置 ExitCode 和 throw。不需要Stop(); - ServiceBase 中的异常处理程序会这样做。
      猜你喜欢
      • 2011-10-13
      • 1970-01-01
      • 1970-01-01
      • 2020-06-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多