mirror of
https://github.com/TeamOctolings/Octobot.git
synced 2025-04-19 16:33:36 +03:00
refactor: split reminder sending into a separate service
This commit is contained in:
parent
a953053f1d
commit
891e31a9a1
3 changed files with 62 additions and 36 deletions
|
@ -81,6 +81,7 @@ public sealed class Program
|
||||||
// Services
|
// Services
|
||||||
.AddSingleton<AccessControlService>()
|
.AddSingleton<AccessControlService>()
|
||||||
.AddSingleton<GuildDataService>()
|
.AddSingleton<GuildDataService>()
|
||||||
|
.AddSingleton<ReminderService>()
|
||||||
.AddSingleton<Utility>()
|
.AddSingleton<Utility>()
|
||||||
.AddHostedService<GuildDataService>(provider => provider.GetRequiredService<GuildDataService>())
|
.AddHostedService<GuildDataService>(provider => provider.GetRequiredService<GuildDataService>())
|
||||||
.AddHostedService<MemberUpdateService>()
|
.AddHostedService<MemberUpdateService>()
|
||||||
|
|
57
TeamOctolings.Octobot/Services/ReminderService.cs
Normal file
57
TeamOctolings.Octobot/Services/ReminderService.cs
Normal file
|
@ -0,0 +1,57 @@
|
||||||
|
using System.Text;
|
||||||
|
using Remora.Discord.API.Abstractions.Objects;
|
||||||
|
using Remora.Discord.API.Abstractions.Rest;
|
||||||
|
using Remora.Discord.Extensions.Embeds;
|
||||||
|
using Remora.Discord.Extensions.Formatting;
|
||||||
|
using Remora.Rest.Core;
|
||||||
|
using Remora.Results;
|
||||||
|
using TeamOctolings.Octobot.Data;
|
||||||
|
using TeamOctolings.Octobot.Extensions;
|
||||||
|
|
||||||
|
namespace TeamOctolings.Octobot.Services;
|
||||||
|
|
||||||
|
public sealed class ReminderService
|
||||||
|
{
|
||||||
|
private readonly IDiscordRestChannelAPI _channelApi;
|
||||||
|
|
||||||
|
public ReminderService(IDiscordRestChannelAPI channelApi)
|
||||||
|
{
|
||||||
|
_channelApi = channelApi;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task TickRemindersAsync(Snowflake guildId, IUser user, List<Reminder> reminders, List<Result> failedResults, CancellationToken ct = default)
|
||||||
|
{
|
||||||
|
for (var i = reminders.Count - 1; i >= 0; i--)
|
||||||
|
{
|
||||||
|
var reminder = reminders[i];
|
||||||
|
if (DateTimeOffset.UtcNow < reminder.At)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
var sendResult = await SendReminderAsync(guildId, user, reminders[i], ct);
|
||||||
|
failedResults.AddIfFailed(sendResult);
|
||||||
|
if (sendResult.IsSuccess)
|
||||||
|
{
|
||||||
|
reminders.RemoveAt(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async Task<Result> SendReminderAsync(Snowflake guildId, IUser user, Reminder reminder, CancellationToken ct = default)
|
||||||
|
{
|
||||||
|
var builder = new StringBuilder()
|
||||||
|
.AppendBulletPointLine(string.Format(Messages.DescriptionReminder, Markdown.InlineCode(reminder.Text)))
|
||||||
|
.AppendBulletPointLine(string.Format(Messages.DescriptionActionJumpToMessage,
|
||||||
|
$"https://discord.com/channels/{guildId.Value}/{reminder.ChannelId}/{reminder.MessageId}"));
|
||||||
|
|
||||||
|
var embed = new EmbedBuilder().WithSmallTitle(
|
||||||
|
string.Format(Messages.Reminder, user.GetTag()), user)
|
||||||
|
.WithDescription(builder.ToString())
|
||||||
|
.WithColour(ColorsList.Magenta)
|
||||||
|
.Build();
|
||||||
|
|
||||||
|
return await _channelApi.CreateMessageWithEmbedResultAsync(
|
||||||
|
reminder.ChannelId.ToSnowflake(), Mention.User(user), embedResult: embed, ct: ct);
|
||||||
|
}
|
||||||
|
}
|
|
@ -31,15 +31,17 @@ public sealed partial class MemberUpdateService : BackgroundService
|
||||||
private readonly IDiscordRestGuildAPI _guildApi;
|
private readonly IDiscordRestGuildAPI _guildApi;
|
||||||
private readonly GuildDataService _guildData;
|
private readonly GuildDataService _guildData;
|
||||||
private readonly ILogger<MemberUpdateService> _logger;
|
private readonly ILogger<MemberUpdateService> _logger;
|
||||||
|
private readonly ReminderService _reminders;
|
||||||
|
|
||||||
public MemberUpdateService(AccessControlService access, IDiscordRestChannelAPI channelApi,
|
public MemberUpdateService(AccessControlService access, IDiscordRestChannelAPI channelApi,
|
||||||
IDiscordRestGuildAPI guildApi, GuildDataService guildData, ILogger<MemberUpdateService> logger)
|
IDiscordRestGuildAPI guildApi, GuildDataService guildData, ILogger<MemberUpdateService> logger, ReminderService reminders)
|
||||||
{
|
{
|
||||||
_access = access;
|
_access = access;
|
||||||
_channelApi = channelApi;
|
_channelApi = channelApi;
|
||||||
_guildApi = guildApi;
|
_guildApi = guildApi;
|
||||||
_guildData = guildData;
|
_guildData = guildData;
|
||||||
_logger = logger;
|
_logger = logger;
|
||||||
|
_reminders = reminders;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override async Task ExecuteAsync(CancellationToken ct)
|
protected override async Task ExecuteAsync(CancellationToken ct)
|
||||||
|
@ -113,11 +115,7 @@ public sealed partial class MemberUpdateService : BackgroundService
|
||||||
return failedResults.AggregateErrors();
|
return failedResults.AggregateErrors();
|
||||||
}
|
}
|
||||||
|
|
||||||
for (var i = data.Reminders.Count - 1; i >= 0; i--)
|
await _reminders.TickRemindersAsync(guildId, user, data.Reminders, failedResults, ct);
|
||||||
{
|
|
||||||
var reminderTickResult = await TickReminderAsync(data.Reminders[i], user, data, guildId, ct);
|
|
||||||
failedResults.AddIfFailed(reminderTickResult);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!canInteract)
|
if (!canInteract)
|
||||||
{
|
{
|
||||||
|
@ -224,34 +222,4 @@ public sealed partial class MemberUpdateService : BackgroundService
|
||||||
|
|
||||||
[GeneratedRegex("[^0-9A-Za-zА-Яа-яЁё]")]
|
[GeneratedRegex("[^0-9A-Za-zА-Яа-яЁё]")]
|
||||||
private static partial Regex IllegalChars();
|
private static partial Regex IllegalChars();
|
||||||
|
|
||||||
private async Task<Result> TickReminderAsync(Reminder reminder, IUser user, MemberData data, Snowflake guildId,
|
|
||||||
CancellationToken ct)
|
|
||||||
{
|
|
||||||
if (DateTimeOffset.UtcNow < reminder.At)
|
|
||||||
{
|
|
||||||
return Result.Success;
|
|
||||||
}
|
|
||||||
|
|
||||||
var builder = new StringBuilder()
|
|
||||||
.AppendBulletPointLine(string.Format(Messages.DescriptionReminder, Markdown.InlineCode(reminder.Text)))
|
|
||||||
.AppendBulletPointLine(string.Format(Messages.DescriptionActionJumpToMessage,
|
|
||||||
$"https://discord.com/channels/{guildId.Value}/{reminder.ChannelId}/{reminder.MessageId}"));
|
|
||||||
|
|
||||||
var embed = new EmbedBuilder().WithSmallTitle(
|
|
||||||
string.Format(Messages.Reminder, user.GetTag()), user)
|
|
||||||
.WithDescription(builder.ToString())
|
|
||||||
.WithColour(ColorsList.Magenta)
|
|
||||||
.Build();
|
|
||||||
|
|
||||||
var messageResult = await _channelApi.CreateMessageWithEmbedResultAsync(
|
|
||||||
reminder.ChannelId.ToSnowflake(), Mention.User(user), embedResult: embed, ct: ct);
|
|
||||||
if (!messageResult.IsSuccess)
|
|
||||||
{
|
|
||||||
return ResultExtensions.FromError(messageResult);
|
|
||||||
}
|
|
||||||
|
|
||||||
data.Reminders.Remove(reminder);
|
|
||||||
return Result.Success;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue