【问题标题】:Windows service on Local Computer started and then stopped error本地计算机上的 Windows 服务启动然后停止错误
【发布时间】:2012-08-25 21:38:10
【问题描述】:

通常,我收到此错误: (本地计算机上的“服务名称”服务启动然后停止。如果某些服务没有被其他服务或程序使用,它们会自动停止)当我的代码出现问题时,例如不存在的驱动器路径等。Windows服务不会启动。

我有一个 Windows 服务,可以将文件夹/文件备份到某个位置(如果它达到大小限制)。详细信息均由 Windows 服务在启动时读取的 XML 配置提供。我有一个单独的 Windows 窗体,它有一个按钮,它完全符合我的 Windows 服务的 onstart 正在做的事情。在将代码放入我的 Windows 服务之前,我使用我的 Windows 窗体来调试代码。

当我启动我的 Windows 窗体时。它做它应该做的事情。当我将代码放入 Windows 服务的 OnStart() 方法时,出现了错误。

这是我的代码:

protected override void OnStart(string[] args)
{

    private static string backupConfig = @"D:\LogBackupConfig\backupconfig.xml";
    private static string serviceStat = @"D:\LogBackupConfig\Status.txt";
    private static string fileFolderStat = @"D:\LogBackupConfig\FileFolderStat.txt";

    protected override void OnStart(string[] args)
    {
        if (File.Exists(backupConfig))
        {
            FileSystemWatcher watcher = new FileSystemWatcher();
            XmlTextReader reader = new XmlTextReader(backupConfig);

            XmlNodeType type;
            List<string> listFile = new List<string>();
            string fileWatch = "";

            //this loop is for reading XML elements and assigning to variables
            while (reader.Read())
            {
                type = reader.NodeType;
                if (type == XmlNodeType.Element)
                {
                    if (reader.Name == "File")
                    {
                        reader.Read();
                        fileWatch = reader.Value;
                    }
                    else if (reader.Name == "Folder")
                    {
                        reader.Read();
                        fileWatch = reader.Value;
                    }
                }
            }
            reader.Close();

            watcher.Path = fileWatch;
            watcher.Filter = "*.*";

            //this loop reads whether the service will watch a file/folder
            XmlTextReader reader1 = new XmlTextReader(backupConfig);
            while (reader1.Read())
            {
                type = reader1.NodeType;
                if (type == XmlNodeType.Element)
                {
                    if (reader1.Name == "File")
                    {
                        watcher.IncludeSubdirectories = false;
                        watcher.Changed += new FileSystemEventHandler(OnChangedFile);
                    }
                    else if (reader1.Name == "Folder")
                    {
                        watcher.IncludeSubdirectories = true;
                        watcher.Changed += new FileSystemEventHandler(OnChangedFolder);
                    }
                }
            }
            reader1.Close();

            watcher.EnableRaisingEvents = true;

        }
        else
        {
            StreamWriter sw = new StreamWriter(serviceStat, true);
            sw.WriteLine("File not found. Please start the Log Backup UI first.");
            sw.Close();
        }
    }

我不知道是什么让 windows 服务无法启动,windows 窗体模拟器工作正常。似乎是什么问题?

更新: 经过多次试验,我注意到仅使用文件夹目录(无文件),Windows 服务不起作用。当我用特定文件(包括其目录)替换 fileWatch 变量时,Windows 服务启动。当我将其更改回文件夹位置时,它不起作用。我认为文件夹位置在文件观察器中不起作用。

当我尝试创建一个监视文件夹位置的新 Windows 服务时,它可以工作。但是,当我在原始 Windows 服务中尝试相同的位置时,它没有工作!我很介意$#*!似乎每次我放置一个新的代码/功能时,我都必须创建一个新的 Windows 服务并构建安装程序。这样我就可以跟踪我得到错误的地方。

【问题讨论】:

    标签: c# windows-services


    【解决方案1】:

    在我们的例子中,Windows 事件日志中没有添加任何内容,除了有问题的服务已启动然后停止的日志。

    原来服务的 CONFIG 文件无效。更正无效的 CONFIG 文件解决了该问题。

    【讨论】:

      【解决方案2】:

      同时,另一个原因:不小心删除了.config文件导致出现同样的错误信息:

      “本地计算机上的服务启动然后停止。一些服务自动停止...”

      【讨论】:

        【解决方案3】:

        EventLog.Log 应设置为“应用程序”

        【讨论】:

        • 我刚刚投了赞成票,因为这对我来说实际上是解决问题的方法
        【解决方案4】:

        我发现将现有的 windows 服务 转换为 console 非常方便,只需使用以下内容更改您的程序即可。通过此更改,您可以通过在 Visual Studio 中调试或正常运行可执行文件来运行程序。但它也可以用作 Windows 服务。 I also made a blog post about it

        program.cs

        class Program
        {
            static void Main()
            {
                var program = new YOUR_PROGRAM();
                if (Environment.UserInteractive)
                {
                    program.Start();
                }
                else
                {
                    ServiceBase.Run(new ServiceBase[]
                    {
                        program
                    });
                }
            }
        }
        

        YOUR_PROGRAM.cs

        [RunInstallerAttribute(true)]
        public class YOUR_PROGRAM : ServiceBase
        {
            public YOUR_PROGRAM()
            {
                InitializeComponent();
            }
        
            protected override void OnStart(string[] args)
            {
                Start();
            }
        
            protected override void OnStop()
            {
                //Stop Logic Here
            }
        
            public void Start()
            {
                //Start Logic here
            }
        }
        

        【讨论】:

          【解决方案5】:

          我遇到了同样的问题。我的服务正在上传/接收 XMLS 并将错误写入事件日志。

          当我查看事件日志时,我尝试对其进行过滤。它提示我事件日志已损坏。

          我清除了事件日志,一切正常。

          【讨论】:

            【解决方案6】:

            请检查您是否已在本地机器的访问控制列表 (ACL) 中注册了所有 HTTP 端点

            http://just2thepoint.blogspot.fr/2013/10/windows-service-on-local-computer.html

            【讨论】:

              【解决方案7】:

              如果服务以这种方式启动和停止,则意味着您的代码正在引发未处理的异常。这很难调试,但有几个选项。

              1. 请参阅 Windows 事件查看器。通常,您可以通过转到计算机/服务器管理器,然后单击 Event Viewer -> Windows 日志 -> 应用程序 来完成此操作。您可以在此处查看引发异常的原因,这可能会有所帮助,但您不会获得堆栈跟踪。
              2. 将程序逻辑提取到库类项目中。现在创建两个不同版本的程序:控制台应用程序(用于调试)和 Windows 服务。 (这是一些初步的努力,但从长远来看可以省去很多焦虑。)
              3. 添加更多 try/catch 块并将日志记录到应用程序以更好地了解正在发生的事情。

              【讨论】:

              • Windows 事件查看器显示了完整的堆栈跟踪,非常有用的工具。
              • 非常感谢。我最近卸载了 JRE,无法重新启动 Jenkins 服务,因为它指向已删除的 JRE bin 目录。必须在jenkins.xmlexecutable 标记中配置新路径。我发现这个答案真的很有帮助! +1。
              【解决方案8】:

              运行该服务的帐户可能没有映射 D:-drive(它们是用户特定的)。尝试共享目录,并在 backupConfig 中使用完整的 UNC 路径。

              您的FileSystemWatcher 类型的watcher 是一个局部变量,并且在OnStart 方法完成时超出范围。您可能需要它作为实例或类变量。

              【讨论】:

                【解决方案9】:

                不确定这是否会有所帮助,但对于调试服务,您始终可以在 OnStart 方法中使用以下内容:

                protected override void OnStart(string[] args)
                {
                     System.Diagnostics.Debugger.Launch();
                     ...
                }
                

                您可以将您的视觉工作室附加到流程中并拥有更好的调试能力。

                希望这有帮助, 祝你好运

                【讨论】:

                • 这是迄今为止最好的解决方案(至少对我而言)。 VS 2015 也很好地处理了这个问题。对我来说,它为 JIT 调试器弹出了一个 UAC 确认对话框,然后让我选择 VS 2015 作为调试器。
                【解决方案10】:

                您可能想要对初始化进行单元测试 - 但因为它在 OnStart 方法中,这几乎是不可能的。我建议将初始化代码移到一个单独的类中,以便可以对其进行测试,或者至少可以在表单测试器中重新使用它。

                其次添加一些日志记录(使用Log4Net 或类似的)并添加一些详细的日志记录,以便您可以查看有关运行时错误的详细信息。运行时错误的示例是 AccessViolation 等,尤其是在您的服务运行时没有足够的权限访问配置文件时。

                【讨论】:

                  【解决方案11】:

                  使用计时器和滴答事件来复制您的文件。

                  在启动服务时,启动时间并指定时间间隔。

                  所以服务会继续运行并复制文件。

                  希望对您有所帮助。

                  【讨论】:

                    猜你喜欢
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 2016-10-21
                    • 2016-06-10
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    相关资源
                    最近更新 更多