private async Task PullAndProcessTasksAsync(CancellationToken cancellationToken) { List <Task> runningTasks = new List <Task>(); while (!cancellationToken.IsCancellationRequested) { Task intervalDelayTask = Task.Delay(TimeSpan.FromSeconds(PollingFrequencyInSeconds), CancellationToken.None); if (runningTasks.Count >= MaxRunningTaskCount) { _ = await Task.WhenAny(runningTasks.ToArray()); runningTasks.RemoveAll(t => t.IsCompleted); } IReadOnlyCollection <TaskInfo> nextTasks = null; try { nextTasks = await _consumer.GetNextMessagesAsync((short)(MaxRunningTaskCount - runningTasks.Count), TaskHeartbeatTimeoutThresholdInSeconds, cancellationToken); } catch (Exception ex) { _logger.LogError(ex, "Failed to pull new tasks."); } if (nextTasks != null && nextTasks.Count > 0) { foreach (TaskInfo taskInfo in nextTasks) { runningTasks.Add(ExecuteTaskAsync(taskInfo, cancellationToken)); } } await intervalDelayTask; } try { await Task.WhenAll(runningTasks.ToArray()); } catch (Exception ex) { _logger.LogError(ex, "Task failed to execute"); } }