Создайте комбинированную командную строку / приложение-службу Windows - PullRequest
11 голосов
/ 01 мая 2009

Каков наилучший способ в C # настроить служебное приложение, которое можно запускать из командной строки и выводить некоторый вывод (или записывать в файл), но его также можно запускать как службу Windows, чтобы выполнять свою работу в фоновом режиме (например, мониторинг каталога или что-то еще).

Я хотел бы написать код один раз и иметь возможность интерактивно вызывать его из PowerShell или из другого интерфейса командной строки, но в то же время найти способ установить тот же файл EXE, что и служба Windows, и запустить его без присмотра. .

Могу ли я сделать это? И если так: как я могу это сделать?

Ответы [ 4 ]

18 голосов
/ 01 мая 2009

Да, вы можете.

Один из способов сделать это - использовать параметр командной строки, скажем, "/ console", чтобы отличить версию консоли от версии запуска в качестве службы:

  • создайте консольное приложение Windows, а затем
  • в Program.cs, точнее в функции Main вы можете проверить наличие параметра "/ console"
  • если есть "/ console", запустить программу как обычно
  • если param отсутствует, вызвать ваш класс Service из ServiceBase

<code>
// Class that represents the Service version of your app
public class serviceSample : ServiceBase
{
    protected override void OnStart(string[] args)
    {
        // Run the service version here 
        //  NOTE: If you're task is long running as is with most 
        //  services you should be invoking it on Worker Thread 
        //  !!! don't take too long in this function !!!
        base.OnStart(args);
    }
    protected override void OnStop()
    {
        // stop service code goes here
        base.OnStop();
    }
}

...

Затем в Program.cs:


static class Program
{
    // The main entry point for the application.
    static void Main(string[] args)
    {
        ServiceBase[] ServicesToRun;</p>

<pre><code>    if ((args.Length > 0) && (args[0] == "/console"))
    {
        // Run the console version here
    }
    else
    {
        ServicesToRun = new ServiceBase[] { new serviceSample () };
        ServiceBase.Run(ServicesToRun);
    }
}

}

4 голосов
/ 01 мая 2009

Лучший способ сделать это с точки зрения дизайна - реализовать все свои функциональные возможности в библиотечном проекте и создать вокруг него отдельные проекты-оболочки для выполнения желаемого способа (например, службы Windows, программы командной строки, ASP). сетевой веб-сервис, сервис wcf и т. д.)

3 голосов
/ 01 мая 2009

Да, это может быть сделано.

Ваш класс запуска должен расширять ServiceBase.

Вы можете использовать ваш метод запуска static void Main (string [] args) для разбора ключа командной строки для запуска в режиме консоли.

Что-то вроде:

static void Main(string[] args)
{
   if ( args == "blah") 
   {
      MyService();
   } 
   else 
   {
      System.ServiceProcess.ServiceBase[] ServicesToRun;
      ServicesToRun = new System.ServiceProcess.ServiceBase[] { new MyService() };
      System.ServiceProcess.ServiceBase.Run(ServicesToRun);
   }
1 голос
/ 01 мая 2009

Служба Windows сильно отличается от обычной программы Windows; вам лучше не пытаться делать две вещи одновременно.

Рассматривали ли вы вместо этого задачу по расписанию?

служба Windows vs запланированное задание

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...