Приветствую всех сегодня рассмотрим тему касающуюся создание служб на C# под Windows.
Службы Microsoft Windows (NT-Services) – это процессы, выполняющиеся в фоновом режиме, не имеющие пользовательского интерфейса и работающие в отдельном сеансе. Службы могут запускаться автоматически при загрузке компьютера, даже если пользователь не вошел в систему.
Для мониторинга и управления службами Windows можно применять доступную в консоли ММС оснастку Services (Службы), которая находится в узле Computer Management (Управление компьютером).
Запустить Службу компонентов, можно выбрать Пуск>Средства администрирования>Служба компонентов
Перед вами запуститься консоль управлением службами установленными у вас системе:
Службу компонентов можно так же запустить другим способом, открыть консоль win+r и ввести services.msc
Создание службы:
Для этого запустите Visual Studio выберите Фаил>Создать проект>Служба Windows
В этом примере я покажу как программно создать службу без использования конструктора:
После запуска проекта, переходим в код программы, в моем случаи он выглядит так:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
using System.Data; using System.Diagnostics; using System.Linq; using System.ServiceProcess; using System.Text; using System.Threading.Tasks; namespace __MyService__ { public partial class Service1 : ServiceBase { public Service1() { InitializeComponent(); } protected override void OnStart(string[] args) { } protected override void OnStop() { } } } |
Обратите внимание, мы работаем в файле Service1.cs наследуемый от System.ServiceProcess.ServiceBase. а не в Program.cs
ServiceBase — базовый класс для службы, которая будет существовать в рамках служебного приложения. При создании нового класса службы, его необходимо унаследовать от класса ServiceBase.
Теперь зададим логику нашей программы, к примеру наша служба будет сохранять в фаил время запуска компьютера и время завершения работы.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
using System; using System.ServiceProcess; namespace __MyService__ { public partial class Service1 : ServiceBase { public Service1() { InitializeComponent(); CanShutdown = true; CanHandleSessionChangeEvent = true; } protected override void OnStart(string[] args) { } protected override void OnStop() { } protected override void OnSessionChange(SessionChangeDescription changeDescription) { if (changeDescription.Reason == SessionChangeReason.SessionLogoff) { using (System.IO.StreamWriter file = new System.IO.StreamWriter(@"C:\LogWork.txt", true)) { file.WriteLine("Выключен: " + DateTime.Now.ToString()); } } if (changeDescription.Reason == SessionChangeReason.SessionLogon) { using (System.IO.StreamWriter file = new System.IO.StreamWriter(@"C:\LogWork.txt", true)) { file.WriteLine("Включен: " + DateTime.Now.ToString()); } } base.OnSessionChange(changeDescription); } } } |
Для этого мы переопределили метод который выполняется при получении события изменения от сеанса сервера терминалов. При возникновении события, происходит вызов метода, и проверка условий, включения или выключения компьютера.
Основной класс у нас готов, теперь нужно создать класс установщик. Так как перед запуском службы Windows ее необходимо установить при этом служба будет зарегистрирована с помощью диспетчера управления службами. В проект можно добавить установщики, которые обрабатывают сведения о регистрации.
Для этого выберите наш проект и нажмите правую кнопку мыши, выберите добавить компонент, перед вами откроется окно в котором вам нужно выбрать Класс установщик, как показано ниже:
Настройки произвел в конструкторе студии таким образом:
Перейдем к коду этого класса, в нем я так же рассмотрел способ того как можно программно включить опцию :
Вход в систему: С системой учетной записью и установил программно галочку Разрешить взаимодействие с рабочим столом. Хотя судя из документации говориться что это сделать не возможно. Но я так понял что данная возможность была упразднена и в windows 10 от нее толку нет.
Раньше данная опция позволяла взаимодействовать с пользователем, делать скриншот экрана, и даже перехватывать нажатие клавиш.
Теперь посмотрим сам класс установщика:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
using System.ComponentModel; using System.Configuration.Install; using System.Management; namespace __MyService__ { [RunInstaller(true)] public partial class ProjectInstaller : System.Configuration.Install.Installer { public ProjectInstaller() { InitializeComponent(); } private void serviceProcessInstaller1_Committed(object sender, InstallEventArgs e) { string serviceName = "Service1"; ManagementObjectSearcher ms = new ManagementObjectSearcher("SELECT * FROM Win32_Service WHERE DisplayName = '" + serviceName + "'"); foreach(ManagementObject mo in ms.Get()) { ManagementBaseObject inParams = mo.GetMethodParameters("Change"); inParams["DesktopInteract"] = true; mo.InvokeMethod("Change",inParams,null); break; } } } } |
С созданием сервиса «Службы» мы закончили, все собираем и в итоге получаем фаил exe
Теперь переходим к заключительной части статьи, как установить и удалить службу:
Для этого есть несколько способов.
1. Способ.
Произвести установку с помощью утилиты installutil.exe которая идет с .net framework сделать это можно из командной строки или для автоматизации создать фаил .cmd или .bat внутрь которого поместить следующий код:
C:\Windows\Microsoft.NET\Framework\v4.0.30319\installutil.exe c:\==MyService==.exe
удаление:
C:\Windows\Microsoft.NET\Framework\v4.0.30319\InstallUtil.exe /u c:\==MyService==.exe
2. Способ.
Еще один способ установки службы это осуществить установку сервиса программно из приложения:
Установка:
1 |
ManagedInstallerClass.InstallHelper(new[]{openFileDialog1.FileName}); |
Удаление службы:
1 |
ManagedInstallerClass.InstallHelper(new[] { @"/u", openFileDialog1.FileName }); |
Где openFileDialog1.FileName это путь до приложения сервиса.
На этом все, старался как можно подробней изложить процесс установки и создания службы, а так же привел свой пример того как можно отследить включение\выключения компьютера.