TgBots/Services/BotService.cs

186 lines
8.3 KiB
C#
Raw Normal View History

2024-12-26 03:32:41 +03:00
using System.Security.Cryptography;
using Microsoft.Extensions.Configuration;
using Telegram.Bot;
using Telegram.Bot.Types;
using Telegram.Bot.Types.Enums;
using UserOfTheDayBot.Data;
using UserOfTheDayBot.Model;
namespace UserOfTheDayBot.Services;
public class BotService
{
private readonly ITelegramBotClient _botClient;
private readonly IUserRepository _userRepository;
private readonly IUserOfTheDayRepository _userOfTheDayRepository;
public BotService(IConfiguration configuration, IUserRepository userRepository, IUserOfTheDayRepository userOfTheDayRepository)
{
_botClient = new TelegramBotClient(configuration["BotSettings:BotToken"] ?? Environment.GetEnvironmentVariable("BotSettings_BotToken"));
_userRepository = userRepository;
_userOfTheDayRepository = userOfTheDayRepository;
}
public async Task HandleUpdateAsync(Update update, CancellationToken cancellationToken)
{
if (update.Type == UpdateType.Message && update.Message?.Text != null)
{
var message = update.Message;
if (message.Text.StartsWith("/help"))
{
await _botClient.SendTextMessageAsync(message.Chat.Id, "Уйди. Попробуйте /reg", cancellationToken: cancellationToken);
}
else if (message.Text.StartsWith("/reg"))
{
await RegisterUserAsync(message, cancellationToken);
}
else if (message.Text.StartsWith("/useroftheday"))
{
await HandleUserOfTheDayCommandAsync(message, UserOfTheDayType.UserOfTheDay, cancellationToken);
}
else if (message.Text.StartsWith("/loser"))
{
await HandleUserOfTheDayCommandAsync(message, UserOfTheDayType.LoserOfTheDay, cancellationToken);
}
else if (message.Text.StartsWith("/stat"))
{
await HandleStatCommandAsync(message, cancellationToken);
}
}
}
private async Task RegisterUserAsync(Message message, CancellationToken cancellationToken)
{
try
{
int rowsAffected = await _userRepository.RegisterUserAsync(message.Chat.Id, message.From.Id, message.From.FirstName);
if (rowsAffected > 0)
{
await _botClient.SendTextMessageAsync(message.Chat.Id, "Вы успешно зарегистрированы!", cancellationToken: cancellationToken);
}
else
{
await _botClient.SendTextMessageAsync(message.Chat.Id, "Вы уже зарегистрированы.", cancellationToken: cancellationToken);
}
}
catch (Exception ex)
{
Console.WriteLine($"Error: {ex.Message}");
2024-12-26 03:35:11 +03:00
2024-12-26 03:32:41 +03:00
await _botClient.SendTextMessageAsync(message.Chat.Id, "Произошла ошибка при регистрации. Попробуйте позже.", cancellationToken: cancellationToken);
}
}
private async Task HandleUserOfTheDayCommandAsync(Message message, UserOfTheDayType type, CancellationToken cancellationToken)
{
try
{
2024-12-26 23:51:50 +03:00
var today = message.Date.Date;
Console.WriteLine(message.Date);
2024-12-26 03:32:41 +03:00
var chatId = message.Chat.Id;
if (await _userOfTheDayRepository.IsUserOfTheDaySelectedAsync(chatId, today, type))
{
2024-12-26 23:28:06 +03:00
var responseMessage = type == UserOfTheDayType.UserOfTheDay ? "Пользователь дня уже выбран." : "Пидор дня уже выбран.";
2024-12-26 03:32:41 +03:00
await _botClient.SendTextMessageAsync(chatId, responseMessage, cancellationToken: cancellationToken);
return;
}
var selectedUser = await SelectUserOfTheDayAsync(chatId, today, type);
if (selectedUser.userId is not null)
2024-12-26 03:32:41 +03:00
{
2024-12-26 23:28:06 +03:00
var responseMessage = type == UserOfTheDayType.UserOfTheDay ? "Пользователь дня" : "Пидор дня";
await _botClient.SendTextMessageAsync(chatId, $"{responseMessage}: {selectedUser.userName}", cancellationToken: cancellationToken);
2024-12-26 03:32:41 +03:00
}
else
{
await _botClient.SendTextMessageAsync(chatId, "В чате нет зарегистрированных пользователей.", cancellationToken: cancellationToken);
}
}
catch (Exception ex)
{
Console.WriteLine($"Error: {ex.Message}");
await _botClient.SendTextMessageAsync(message.Chat.Id, "Произошла ошибка при выборе пользователя дня. Попробуйте позже.", cancellationToken: cancellationToken);
}
}
private async Task<(long? userId, string userName)> SelectUserOfTheDayAsync(long chatId, DateTime date, UserOfTheDayType type)
2024-12-26 03:32:41 +03:00
{
var users = (await _userRepository.GetUsersWithNamesAsync(chatId)).ToList();
if (users.Any())
{
using (var rng = RandomNumberGenerator.Create())
{
while (users.Count > 0)
{
var randomIndex = GetRandomIndex(users.Count, rng);
var selectedUser = users[randomIndex];
if (!await _userOfTheDayRepository.IsUserAlreadySelectedAsync(chatId, date, selectedUser.userId))
{
await _userOfTheDayRepository.RecordUserOfTheDayAsync(chatId, selectedUser.userId, date, type);
return (selectedUser.userId, selectedUser.userName);
2024-12-26 03:32:41 +03:00
}
users.RemoveAt(randomIndex);
}
}
}
return default;
2024-12-26 03:32:41 +03:00
}
private async Task HandleStatCommandAsync(Message message, CancellationToken cancellationToken)
{
try
{
var chatId = message.Chat.Id;
var stats = await _userOfTheDayRepository.GetUserStatisticsAsync(chatId);
if (stats.Any())
{
var userOfTheDaySection = "Пользователь дня:\n";
2024-12-26 23:28:06 +03:00
var loserOfTheDaySection = "Пидор дня:\n";
2024-12-26 03:32:41 +03:00
var sortedUserOfTheDay = stats.OrderByDescending(x => x.Value.userOfTheDayCount);
var sortedLoserOfTheDay = stats.OrderByDescending(x => x.Value.loserOfTheDayCount);
foreach (var stat in sortedUserOfTheDay)
{
userOfTheDaySection += $"{stat.Key.userName}: {stat.Value.userOfTheDayCount} раз(а)\n";
}
foreach (var stat in sortedLoserOfTheDay)
{
loserOfTheDaySection += $"{stat.Key.userName}: {stat.Value.loserOfTheDayCount} раз(а)\n";
}
var response = userOfTheDaySection + "\n" + loserOfTheDaySection;
await _botClient.SendTextMessageAsync(chatId, response, cancellationToken: cancellationToken);
}
else
{
await _botClient.SendTextMessageAsync(chatId, "Нет данных о пользователях.", cancellationToken: cancellationToken);
}
}
catch (Exception ex)
{
Console.WriteLine($"Error: {ex.Message}");
await _botClient.SendTextMessageAsync(message.Chat.Id, "Произошла ошибка при получении статистики. Попробуйте позже.", cancellationToken: cancellationToken);
}
}
private static int GetRandomIndex(int max, RandomNumberGenerator rng)
{
var buffer = new byte[4];
rng.GetBytes(buffer);
var randomValue = BitConverter.ToUInt32(buffer, 0);
return (int)(randomValue % max);
}
}