ایجاد Worker Service

برای ایجاد کارهایی که نیاز به توان پردازش بیشتر، پردازش صف‌های طولانی دیتا یا مواردی که زمان طولانی‌تر برای محاسبات نیاز دارند می‌توان از WindowsServiceها و یا WorkerServiceها استفاده کرد.

هر دو مورد شباهتها و عملکردهای مشابه‌ای دارند اما در برخی موارد نیز تفاوت‌های دیده می‌شود که در مورد پیشرفته‌تر حائز اهمیت می‌شوند.
تفاوتهای این دو عبارتند از:

WindowsServiceWorkerService
1. اپلیکشن سرویس‌هایی با دوره اجرای در طی یک نشست ویندوزی (Windows Session).
2. داشتن تنظیمات بیشتر در ایجاد یک سرویس.
3. به عنوان یک NT Service شناخته می‌شوند.
4. عدم امکان دیباگ کردن در VisualStudio.
5. اجبار به داشتن جزء Installation در ساختن یک سرویس (لینک).
6. امکان اجرا در جایگاه متفاوتی نسبت به جایگاه کاربر وارد شده به سیستم.
1. معرفی شده در Net Core 3.0
2. راحتی استفاده از ویژگی‌های Core مثل Dependency Injection, Logging and Configuration.
3. امکان دیباگ کردن.
4. اجرا بر روی process host متعلق به خود سرویس.
5. امکان ایجاد سرویس بر روی سایر پلتفرم‌ها.

برای اینکه WorkerService شما به عنوان یک ویندوزسرویس شناخته شود، کافی است در متد Configuration کد UseWindowsService را اضافه کنید:

IHost host = Host.CreateDefaultBuilder(args)
    .ConfigureServices(services =>
    {
        services.AddHostedService<Worker>();
        var optionBuilder = new DbContextOptionsBuilder<Gateway.Infrastructure.DB_Models.PaymentmanagementsystemContext>();

        services.AddScoped(x => new Gateway.Infrastructure.DB_Models.PaymentmanagementsystemContext(optionBuilder.Options));

    })
    .UseWindowsService(option =>
    {
        /*force app to work as windows service*/
        option.ServiceName = "SIPAD.TransactionDate.ServiceWorker";
    })    
    .Build();

await host.RunAsync();

نکته!
برای استفاده از سرویس‌هایی که به شکل AddScoped تزریق شده‌اند (سایر روشهای تزریق قابل قبول نیستند!) نیاز است که در کلاس Worker خودتون از این روش متدهای مورد نیاز را فراخوانی کنید:

using (var scope = serviceProvider.CreateScope())
{
	try
	{
		//Get last sorathesabid in extracted table
		var lastId = await scope.ServiceProvider.GetRequiredService<ISoratHesab_TransactionDate>().GetLastSorathesabId();
		if (lastId > 0)
		{
			//ToDo
		}
		else
		{
			_logger.LogError($"SorathesabId has error - {nameof(lastId)}:{lastId}");
		}
	}
	catch (Exception err)
	{
		_logger.LogCritical(err.Message);
	}
}

بعد از پابیلیش WorkerService خودتون با دستور زیر آن را به عنوان سرویس به ویندوز معرفی کنید:

sc.exe create "TestService" binpath="C:\Path\To\TestService.exe"

منبع