コード例 #1
0
        protected override async Task ExecuteAsync(CancellationToken token)
        {
            // Create a token that can be cancelled to stop all running tasks
            var tokenSource = CancellationTokenSource.CreateLinkedTokenSource(token);

            // Execute startup activities and upon success send a startup signal
            await SendStartedSignalAsync(tokenSource.Token).ConfigureAwait(false);

            // Start sending liveness signal periodically
            var signalParallelTask = SendAliveSignalAsync(TimeSpan.FromSeconds(_probeConfiguration.LivenessSignalIntervalSeconds), tokenSource.Token);

            // Paralllelly execute background worker's jobs
            var workerParallelTask = _serviceImplementation.ExecuteAsync(tokenSource.Token);

            // If liveness or worker job throws exception or runs to completion then cancel everything and exit the program.
            var continuationTask = await Task.WhenAny(signalParallelTask, workerParallelTask).ConfigureAwait(false);

            // Awaiting on task returned by Task.WhenAny() bubbles exceptions in inner tasks
            await continuationTask.ConfigureAwait(false);

            // If any one of then run to completion then cancel the other
            await continuationTask.ContinueWith(t => tokenSource.Cancel()).ConfigureAwait(false);

            // Although all tasks will finish by now, background service will not cause the host to terminate.
            // You will have to implement IApplicationLifetime for that which may not make sense if there are multiple IHostedService implemented.
            // But, since kubernetes liveness probes are enabled, absence of alive.signal file will cause service to reboot.
        }