.NET 애플리케이션을 윈도 서비스로 실행하는 방법을 소개합니다. 다만 디버그 및 서비스 등록을 좀 더 편하게 하려면 Topshelf가 여전히 유용한 선택지입니다.
와… 딱 지금 제가 하고 있는 작업이네요…ㅇㅅㅇb
근데
예제를 검색해보면 대부분 BackgroundService 를 상속받는 Worker 클래스를 이용하는데요
굳이 그렇게 할 필요는 없숨다.
그냥 편하게 기존 .NET6 방식의 호스팅 작업처럼 구성하시고
진입점으로 사용할 개체만 HostedService 로 등록해주면 됩니다.
대신 진입점으로 사용할 개체는 IHostedService
인터페이스를 구현해주셔야 합니닷.
public class MyHostedService : IHostedService
{
readonly ILogger<MyHostedService> _logger;
public MyHostedService(ILogger<MyHostedService> logger)
{
_logger = logger;
}
public Task StartAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("MyHostedService started");
// 뭔가 여기서 서비스를 위한 로직을 호출!
return Task.CompletedTask;
}
public async Task StopAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("MyHostedService stopping...");
await Task.Delay(10_000);
_logger.LogInformation("MyHostedService stopped");
}
}
그리고 요녀석을 등록해서
// Program.cs top-level-state 입니다.
var host = Host.CreateDefaultBuilder(args)
.UseWindowsService(options =>
{
options.ServiceName = "My windows service";
})
.ConfigureServices((hostContext, services) =>
{
// 하던대로 여기서 필요한 거 세팅 후
// MyHostedService 를 호스트로 등록
services.AddHostedService<MyHostedService>();
})
.Build();
await host.RunAsync();
await host.WaitForShutdownAsync();
요렇게 하시면
MyHostedService
를 진입점으로 이용하는 Windows service 를 만들 수 있어욤.
이렇게 하고 바이너리 뽑아서 sc.exe create {서비스 이름} binPath={바이너리 경로}
해주면 서비스 등록되고
(Windows 한정입니다. 리눅스는 다른 방법으루…)
서비스로 시작하면 실행됩니다.
VS 로 디버깅이 하고 싶으시면
서비스 실행 후 Debug → process to attach 해서 해당 프로세스에 붙으면 되고
시작부터 디버깅 붙이고 싶으면 디버깅 붙이고 싶은 위치에
System.Diagnostics.Debugger.Launch();
해주면 해당 위치에서 “너 디버깅 붙일거야?” 하고 물어봅니다.
대략 이런 식으로 개발하면 됩니닷.
하지만 난 하루 종일 헤딩을 했고…;;;;
일전에 제가 .NET 5로 Windows Service를 만들어본 경험도 공유합니다.
Microsoft.Extensions.Hosting.WindowsServices 패키지로 윈도우 서비스를 작성하고 배포 해도 좋을 것 같네요.
TopShelf에 대한 얘기인줄 알았는데 같은 주제였군요