Как настроить реализацию Daemon в качестве службы Windows

Я не нашел действительно хорошего примера (на самом деле я не нашел ни одного примера) того, как зарегистрировать класс, реализующий интерфейс org.apache.commons.daemon.Daemon, как службу Windows.

Нужно ли регистрировать эту реализацию с помощью procrun? Но тогда кажется, что нет смысла реализовывать интерфейс, так как procrun может зарегистрировать любую программу как службу Windows.

Кроме того, похоже, что на странице procrun есть ошибка документа (http://commons.apache.org/proper/commons-daemon/procrun.html):

В описании параметра --StartMethod указано:

Примечание: в режиме jvm метод запуска не должен возвращаться, пока не будет вызван метод остановки.

Но далее по странице в разделе «Использование Procrun в режиме jvm»:

Обратите внимание, что запуск службы обработки метода должен создать и запустить отдельный поток для выполнения обработки, а затем вернуться. Методы start и stop вызываются из разных потоков.

Я неправильно читаю или это немного противоречиво?? И каким было бы правильное поведение статического метода start(String[] args)?

С наилучшими пожеланиями


person dpr    schedule 22.07.2015    source источник


Ответы (1)


Для записей:

Нужно ли регистрировать эту реализацию с помощью procrun? Но тогда кажется, что нет смысла реализовывать интерфейс, так как procrun может зарегистрировать любую программу как службу Windows.

Да, сервис должен быть зарегистрирован в Windows с помощью prunsrv. Например, со следующим вызовом:

prunsrv.exe //IS//MyTestService ^
    --DisplayName="My Test Service" --Description="Doesn't really do anything" ^
    --Install=@@PATH_TO_PRUNSRV@@\prunsrv.exe ^
    --Startup=manual ^
    --Jvm=auto ^
    --Classpath="@@PUT_FULL_CLASSPATH_HERE@@" ^
    --StartMode=jvm ^
    --StartClass==com.stackoverflow.questions.31556478.ServiceLauncher ^
    --StartParams="@@PUT_ANY_START_ARGUMENTS_HERE@@" ^
    --StartMethod=start ^
    --StopMode=jvm ^
    --StopClass=com.stackoverflow.questions.31556478.ServiceLauncher ^
    --StopMethod=stop

После этого сервис может быть запущен с помощью

prunsrv //ES//MyTestSevice


И каким было бы правильное поведение статического метода start(String[] args)?

При тестировании обоих вариантов работала только реализация, которая оставалась в start-методе и не порождала дополнительных потоков. Это реализация запуска, которую можно зарегистрировать с помощью приведенного выше вызова prunsrv, будет выглядеть примерно так (без каких-либо гарантий):

package com.stackoverflow.questions.31556478;

import java.util.Arrays;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class ServiceLauncher
{
  private static final Logger LOGGER = LoggerFactory.getLogger(ServiceLauncher.class);

  private static SomeServer mServer;

  public static void start(final String[] args)
  {
    LOGGER.debug("Start called: {}", Arrays.toString(args));

    try
    {
      mServer = new SomeServer(args);
      mServer.start();
    }
    catch (final Exception e)
    {
      LOGGER.error("Terminating due to Exception: ", e);
    }
  }

  public static void stop(final String[] args) throws Exception
  {
    LOGGER.debug("Stop called: {}", Arrays.toString(args));

    synchronized (ServiceLauncher.class)
    {
      if (mServer != null)
      {
        mServer.stop();
      }
    }
  }
}
person dpr    schedule 02.09.2015