work on repeater
This commit is contained in:
@@ -1,130 +1,106 @@
|
||||
using Discord;
|
||||
using Discord.Commands;
|
||||
using NadekoBot.Classes;
|
||||
using NadekoBot.Modules.Permissions.Classes;
|
||||
using NadekoBot.Attributes;
|
||||
using NadekoBot.Services;
|
||||
using NadekoBot.Services.Database;
|
||||
using NadekoBot.Services.Database.Models;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using System.Timers;
|
||||
|
||||
//todo DB
|
||||
namespace NadekoBot.Modules.Administration
|
||||
{
|
||||
class MessageRepeater : DiscordCommand
|
||||
public partial class Administration
|
||||
{
|
||||
private readonly ConcurrentDictionary<Server, Repeater> repeaters = new ConcurrentDictionary<Server, Repeater>();
|
||||
private class Repeater
|
||||
|
||||
[Group]
|
||||
public class RepeatCommands
|
||||
{
|
||||
[Newtonsoft.Json.JsonIgnore]
|
||||
public Timer MessageTimer { get; set; }
|
||||
[Newtonsoft.Json.JsonIgnore]
|
||||
public Channel RepeatingChannel { get; set; }
|
||||
public ConcurrentDictionary<ulong, Repeater> repeaters;
|
||||
|
||||
public ulong RepeatingServerId { get; set; }
|
||||
public ulong RepeatingChannelId { get; set; }
|
||||
public Message lastMessage { get; set; } = null;
|
||||
public string RepeatingMessage { get; set; }
|
||||
public int Interval { get; set; }
|
||||
|
||||
public Repeater Start()
|
||||
public RepeatCommands()
|
||||
{
|
||||
MessageTimer = new Timer { Interval = Interval };
|
||||
MessageTimer.Elapsed += async (s, e) => await Invoke();
|
||||
return this;
|
||||
}
|
||||
|
||||
public async Task Invoke()
|
||||
{
|
||||
var ch = RepeatingChannel;
|
||||
var msg = RepeatingMessage;
|
||||
if (ch != null && !string.IsNullOrWhiteSpace(msg))
|
||||
using (var uow = DbHandler.UnitOfWork())
|
||||
{
|
||||
try
|
||||
{
|
||||
if (lastMessage != null)
|
||||
await lastMessage.Delete().ConfigureAwait(false);
|
||||
}
|
||||
catch { }
|
||||
try
|
||||
{
|
||||
lastMessage = await ch.SendMessageAsync(msg).ConfigureAwait(false);
|
||||
}
|
||||
catch { }
|
||||
repeaters = new ConcurrentDictionary<ulong, Repeater>(uow.Repeaters.GetAll().ToDictionary(r => r.ChannelId));
|
||||
}
|
||||
}
|
||||
}
|
||||
internal override void Init(CommandGroupBuilder cgb)
|
||||
{
|
||||
|
||||
cgb.CreateCommand(Module.Prefix + "repeatinvoke")
|
||||
.Alias(Module.Prefix + "repinv")
|
||||
.Description($"Immediately shows the repeat message and restarts the timer. **Needs Manage Messages Permissions.**| `{Prefix}repinv`")
|
||||
.AddCheck(SimpleCheckers.ManageMessages())
|
||||
.Do(async e =>
|
||||
[LocalizedCommand, LocalizedDescription, LocalizedSummary]
|
||||
[RequireContext(ContextType.Guild)]
|
||||
[RequirePermission(GuildPermission.ManageMessages)]
|
||||
public async Task RepeatInvoke(IMessage imsg)
|
||||
{
|
||||
var channel = (ITextChannel)imsg.Channel;
|
||||
|
||||
Repeater rep;
|
||||
if (!repeaters.TryGetValue(channel.Id, out rep))
|
||||
{
|
||||
Repeater rep;
|
||||
if (!repeaters.TryGetValue(e.Server, out rep))
|
||||
{
|
||||
await channel.SendMessageAsync("`No repeating message found on this server.`");
|
||||
return;
|
||||
}
|
||||
await channel.SendMessageAsync("`No repeating message found on this server.`").ConfigureAwait(false);
|
||||
return;
|
||||
}
|
||||
|
||||
await rep.Invoke();
|
||||
});
|
||||
await channel.SendMessageAsync("🔄 " + rep.Message);
|
||||
}
|
||||
|
||||
cgb.CreateCommand(Module.Prefix + "repeat")
|
||||
.Description("Repeat a message every X minutes. If no parameters are specified, " +
|
||||
$"repeat is disabled. **Needs Manage Messages Permissions.** |`{Prefix}repeat 5 Hello there`")
|
||||
.Parameter("minutes", ParameterType.Optional)
|
||||
.Parameter("msg", ParameterType.Unparsed)
|
||||
.AddCheck(SimpleCheckers.ManageMessages())
|
||||
.Do(async e =>
|
||||
[LocalizedCommand, LocalizedDescription, LocalizedSummary]
|
||||
[RequireContext(ContextType.Guild)]
|
||||
public async Task Repeat(IMessage imsg, int minutes, [Remainder] string message = null)
|
||||
{
|
||||
var channel = (ITextChannel)imsg.Channel;
|
||||
|
||||
if (minutes < 1 || minutes > 1500)
|
||||
return;
|
||||
|
||||
Repeater rep;
|
||||
|
||||
if (string.IsNullOrWhiteSpace(message)) //turn off
|
||||
{
|
||||
var minutesStr = minutes;
|
||||
var msg = msg;
|
||||
|
||||
// if both null, disable
|
||||
if (string.IsNullOrWhiteSpace(msg) && string.IsNullOrWhiteSpace(minutesStr))
|
||||
if (repeaters.TryRemove(channel.Id, out rep))
|
||||
{
|
||||
|
||||
Repeater rep;
|
||||
if (!repeaters.TryRemove(e.Server, out rep))
|
||||
return;
|
||||
rep.MessageTimer.Stop();
|
||||
await channel.SendMessageAsync("Repeating disabled").ConfigureAwait(false);
|
||||
return;
|
||||
}
|
||||
int minutes;
|
||||
if (!int.TryParse(minutesStr, out minutes) || minutes < 1 || minutes > 1440)
|
||||
{
|
||||
await channel.SendMessageAsync("Invalid value").ConfigureAwait(false);
|
||||
return;
|
||||
}
|
||||
|
||||
var repeater = repeaters.GetOrAdd(
|
||||
e.Server,
|
||||
s => new Repeater
|
||||
using (var uow = DbHandler.UnitOfWork())
|
||||
{
|
||||
Interval = minutes * 60 * 1000,
|
||||
RepeatingChannel = e.Channel,
|
||||
RepeatingChannelId = e.Channel.Id,
|
||||
RepeatingServerId = e.Server.Id,
|
||||
}.Start()
|
||||
);
|
||||
uow.Repeaters.Remove(rep);
|
||||
await uow.CompleteAsync();
|
||||
}
|
||||
await channel.SendMessageAsync("`Stopped repeating a message.`").ConfigureAwait(false);
|
||||
}
|
||||
else
|
||||
await channel.SendMessageAsync("`No message is repeating.`").ConfigureAwait(false);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(msg))
|
||||
repeater.RepeatingMessage = msg;
|
||||
|
||||
repeater.MessageTimer.Stop();
|
||||
repeater.MessageTimer.Start();
|
||||
|
||||
await channel.SendMessageAsync(String.Format("👌 Repeating `{0}` every " +
|
||||
"**{1}** minutes on {2} channel.",
|
||||
repeater.RepeatingMessage, minutes, repeater.RepeatingChannel))
|
||||
.ConfigureAwait(false);
|
||||
rep = repeaters.AddOrUpdate(channel.Id, (cid) =>
|
||||
{
|
||||
using (var uow = DbHandler.UnitOfWork())
|
||||
{
|
||||
var localRep = new Repeater
|
||||
{
|
||||
ChannelId = channel.Id,
|
||||
GuildId = channel.Guild.Id,
|
||||
Interval = TimeSpan.FromMinutes(minutes),
|
||||
Message = message,
|
||||
};
|
||||
uow.Repeaters.Add(localRep);
|
||||
uow.Complete();
|
||||
return localRep;
|
||||
}
|
||||
}, (cid, old) =>
|
||||
{
|
||||
using (var uow = DbHandler.UnitOfWork())
|
||||
{
|
||||
old.Message = message;
|
||||
old.Interval = TimeSpan.FromMinutes(minutes);
|
||||
uow.Repeaters.Update(old);
|
||||
uow.Complete();
|
||||
return old;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
public MessageRepeater(DiscordModule module) : base(module) { }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user