Создание многопоточности для функции с ожиданием
Есть некая функция, выполняющая отправку сообщений с задержкой, используя авторизационный код, сообщение, и временная задержка между сообщениями, подготовленные определенным пользователем.
Мне необходимо, чтобы когда все данные были введены функция начала свою работу для определенного пользователя и продолжала ее пока он не захочет остановить отправку сообщений. Но таких запусков функции будет не одно количество, ведь пользователей бота может быть много.
Сначала для решения этой задачи я создал такой код, который делает что-то похожее на то что я хочу сделать:
bool IsPosting = true;
var task = Post();
await task;
static async Task Post()
{
while(IsPosting) {
Console.WriteLine("Отправка сообщения");
await Task.Delay(5000);
}
}
Но будет если такой код работать корректно, если запустить таким образом 1000+ задач ? Как можно реализовать это более лучшим способом ?
Ответы (1 шт):
Первым делом я рекомендую вам вынести все параметры (а именно сообщение) из вне, дабы его можно было модифицировать для разных задач. После чего для каждой конкретной задачи создать свой объект-контейнер, который будет хранить информацию об этой задачи, а именно: отправляемое сообщение и отменена ли задача.
В итоге получается примерно такой класс:
class MessageSenderTask
{
// Сурс для получения токена для отмены задачи
CancellationTokenSource cts = new();
// Сообщение, которое мы отправляем
public string Message = "";
// Задержка между сообщениями (static потому что она едина для всех)
public static int Delay = 1000;
// Отменить задачу
public void Cancel() => cts.Cancel();
void SendMessage(string message) =>
Console.WriteLine(message);
// Создаём задачу
Task makeTask(CancellationToken cancellationToken) => new Task(async () =>
{
try
{
while (!cancellationToken.IsCancellationRequested)
{
SendMessage(Message);
await Task.Delay(Delay, cancellationToken);
}
}
catch (TaskCanceledException) { }
}, cancellationToken);
// Создаём запущенную задачу
public void Start() => makeTask(cts.Token).Start();
}
Пример использования:
var task1 = new MessageSenderTask() { Message = "Hello from task1" };
var task2 = new MessageSenderTask() { Message = "Hello from task2" };
Task.Delay(1000).Wait();
task1.Start();
task2.Start();
Task.Delay(5000).Wait();
task1.Cancel();
task2.Message = "new message";
Task.Delay(5000).Wait();
task2.Cancel();