Remove all dependencies on redis
This commit is contained in:
parent
2e501008df
commit
33b17b373f
11 changed files with 129 additions and 77 deletions
|
@ -170,23 +170,16 @@ namespace Geekbot.net.Commands.Admin
|
|||
[RequireUserPermission(GuildPermission.ManageRoles)]
|
||||
[Summary("Give a role by clicking on an emoji")]
|
||||
[Command("listen", RunMode = RunMode.Async)]
|
||||
public async Task AddListener([Summary("message-ID")] string messageId, [Summary("Emoji")] string emoji, [Summary("@role")] IRole role)
|
||||
public async Task AddListener([Summary("message-ID")] string messageIdStr, [Summary("Emoji")] string emoji, [Summary("@role")] IRole role)
|
||||
{
|
||||
try
|
||||
{
|
||||
var message = (IUserMessage) await Context.Channel.GetMessageAsync(ulong.Parse(messageId));
|
||||
IEmote emote;
|
||||
if (!emoji.StartsWith('<'))
|
||||
{
|
||||
var emo = new Emoji(emoji);
|
||||
emote = emo;
|
||||
}
|
||||
else
|
||||
{
|
||||
emote = Emote.Parse(emoji);
|
||||
}
|
||||
var messageId = ulong.Parse(messageIdStr);
|
||||
var message = (IUserMessage) await Context.Channel.GetMessageAsync(messageId);
|
||||
var emote = _reactionListener.ConvertStringToEmote(emoji);
|
||||
|
||||
await message.AddReactionAsync(emote);
|
||||
await _reactionListener.AddRoleToListener(messageId, emote, role);
|
||||
await _reactionListener.AddRoleToListener(messageId, Context.Guild.Id, emoji, role);
|
||||
await Context.Message.DeleteAsync();
|
||||
}
|
||||
catch (HttpException e)
|
||||
|
|
|
@ -4,26 +4,25 @@ using System.Threading.Tasks;
|
|||
using Discord.Commands;
|
||||
using Geekbot.net.Database;
|
||||
using Geekbot.net.Database.Models;
|
||||
using Geekbot.net.Lib.AlmostRedis;
|
||||
using Geekbot.net.Lib.ErrorHandling;
|
||||
using Geekbot.net.Lib.Extensions;
|
||||
using Geekbot.net.Lib.KvInMemoryStore;
|
||||
using Geekbot.net.Lib.Localization;
|
||||
using Geekbot.net.Lib.RandomNumberGenerator;
|
||||
using StackExchange.Redis;
|
||||
|
||||
namespace Geekbot.net.Commands.Games
|
||||
{
|
||||
public class Roll : ModuleBase
|
||||
{
|
||||
private readonly IErrorHandler _errorHandler;
|
||||
private readonly IAlmostRedis _redis;
|
||||
private readonly IKvInMemoryStore _kvInMemoryStore;
|
||||
private readonly ITranslationHandler _translation;
|
||||
private readonly DatabaseContext _database;
|
||||
private readonly IRandomNumberGenerator _randomNumberGenerator;
|
||||
|
||||
public Roll(IAlmostRedis redis, IErrorHandler errorHandler, ITranslationHandler translation, DatabaseContext database, IRandomNumberGenerator randomNumberGenerator)
|
||||
public Roll(IKvInMemoryStore kvInMemoryStore,IErrorHandler errorHandler, ITranslationHandler translation, DatabaseContext database, IRandomNumberGenerator randomNumberGenerator)
|
||||
{
|
||||
_redis = redis;
|
||||
_kvInMemoryStore = kvInMemoryStore;
|
||||
_translation = translation;
|
||||
_database = database;
|
||||
_randomNumberGenerator = randomNumberGenerator;
|
||||
|
@ -37,28 +36,28 @@ namespace Geekbot.net.Commands.Games
|
|||
try
|
||||
{
|
||||
var number = _randomNumberGenerator.Next(1, 100);
|
||||
var guess = 1000;
|
||||
int.TryParse(stuff, out guess);
|
||||
int.TryParse(stuff, out var guess);
|
||||
var transContext = await _translation.GetGuildContext(Context);
|
||||
if (guess <= 100 && guess > 0)
|
||||
{
|
||||
var prevRoll = _redis.Db.HashGet($"{Context.Guild.Id}:RollsPrevious2", Context.Message.Author.Id).ToString()?.Split('|');
|
||||
if (prevRoll?.Length == 2)
|
||||
var kvKey = $"{Context.Guild.Id}:{Context.User.Id}:RollsPrevious";
|
||||
|
||||
var prevRoll = _kvInMemoryStore.Get<int>(kvKey);
|
||||
if (prevRoll > 0)
|
||||
{
|
||||
if (prevRoll[0] == guess.ToString() && DateTime.Parse(prevRoll[1]) > DateTime.Now.AddDays(-1))
|
||||
if (prevRoll == guess)
|
||||
{
|
||||
await ReplyAsync(transContext.GetString("NoPrevGuess", Context.Message.Author.Mention));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
_redis.Db.HashSet($"{Context.Guild.Id}:RollsPrevious2", new[] {new HashEntry(Context.Message.Author.Id, $"{guess}|{DateTime.Now}")});
|
||||
_kvInMemoryStore.Set(kvKey, guess);
|
||||
|
||||
await ReplyAsync(transContext.GetString("Rolled", Context.Message.Author.Mention, number, guess));
|
||||
if (guess == number)
|
||||
{
|
||||
await ReplyAsync(transContext.GetString("Gratz", Context.Message.Author));
|
||||
_redis.Db.HashIncrement($"{Context.Guild.Id}:Rolls", Context.User.Id.ToString());
|
||||
var user = await GetUser(Context.User.Id);
|
||||
user.Rolls += 1;
|
||||
_database.Rolls.Update(user);
|
||||
|
|
|
@ -4,7 +4,6 @@ using System.Threading.Tasks;
|
|||
using Discord;
|
||||
using Discord.Commands;
|
||||
using Geekbot.net.Database;
|
||||
using Geekbot.net.Lib.AlmostRedis;
|
||||
using Geekbot.net.Lib.CommandPreconditions;
|
||||
using Geekbot.net.Lib.ErrorHandling;
|
||||
using Geekbot.net.Lib.Extensions;
|
||||
|
@ -16,12 +15,10 @@ namespace Geekbot.net.Commands.User
|
|||
{
|
||||
private readonly IErrorHandler _errorHandler;
|
||||
private readonly ILevelCalc _levelCalc;
|
||||
private readonly IAlmostRedis _redis;
|
||||
private readonly DatabaseContext _database;
|
||||
|
||||
public Stats(IAlmostRedis redis, DatabaseContext database, IErrorHandler errorHandler, ILevelCalc levelCalc)
|
||||
public Stats(DatabaseContext database, IErrorHandler errorHandler, ILevelCalc levelCalc)
|
||||
{
|
||||
_redis = redis;
|
||||
_database = database;
|
||||
_errorHandler = errorHandler;
|
||||
_levelCalc = levelCalc;
|
||||
|
|
|
@ -18,5 +18,6 @@ namespace Geekbot.net.Database
|
|||
public DbSet<RoleSelfServiceModel> RoleSelfService { get; set; }
|
||||
public DbSet<PollModel> Polls { get; set; }
|
||||
public DbSet<CookiesModel> Cookies { get; set; }
|
||||
public DbSet<ReactionListenerModel> ReactionListeners { get; set; }
|
||||
}
|
||||
}
|
22
Geekbot.net/Database/Models/ReactionListenerModel.cs
Normal file
22
Geekbot.net/Database/Models/ReactionListenerModel.cs
Normal file
|
@ -0,0 +1,22 @@
|
|||
using System.ComponentModel.DataAnnotations;
|
||||
|
||||
namespace Geekbot.net.Database.Models
|
||||
{
|
||||
public class ReactionListenerModel
|
||||
{
|
||||
[Key]
|
||||
public int Id { get; set; }
|
||||
|
||||
[Required]
|
||||
public long GuildId { get; set; }
|
||||
|
||||
[Required]
|
||||
public long MessageId { get; set; }
|
||||
|
||||
[Required]
|
||||
public long RoleId { get; set; }
|
||||
|
||||
[Required]
|
||||
public string Reaction { get; set; }
|
||||
}
|
||||
}
|
|
@ -9,12 +9,12 @@ using Discord.Rest;
|
|||
using Discord.WebSocket;
|
||||
using Geekbot.net.Database;
|
||||
using Geekbot.net.Database.Models;
|
||||
using Geekbot.net.Lib.AlmostRedis;
|
||||
using Geekbot.net.Lib.Extensions;
|
||||
using Geekbot.net.Lib.Logger;
|
||||
using Geekbot.net.Lib.ReactionListener;
|
||||
using Geekbot.net.Lib.UserRepository;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
namespace Geekbot.net
|
||||
{
|
||||
public class Handlers
|
||||
|
|
9
Geekbot.net/Lib/KvInMemoryStore/IKvInMemoryStore.cs
Normal file
9
Geekbot.net/Lib/KvInMemoryStore/IKvInMemoryStore.cs
Normal file
|
@ -0,0 +1,9 @@
|
|||
namespace Geekbot.net.Lib.KvInMemoryStore
|
||||
{
|
||||
public interface IKvInMemoryStore
|
||||
{
|
||||
public T Get<T>(string key);
|
||||
public void Set<T>(string key, T value);
|
||||
public void Remove(string key);
|
||||
}
|
||||
}
|
32
Geekbot.net/Lib/KvInMemoryStore/KvInMemoryStore.cs
Normal file
32
Geekbot.net/Lib/KvInMemoryStore/KvInMemoryStore.cs
Normal file
|
@ -0,0 +1,32 @@
|
|||
using System.Collections.Generic;
|
||||
|
||||
namespace Geekbot.net.Lib.KvInMemoryStore
|
||||
{
|
||||
public class KvInInMemoryStore : IKvInMemoryStore
|
||||
{
|
||||
private readonly Dictionary<string, object> _storage = new Dictionary<string, object>();
|
||||
|
||||
public T Get<T>(string key)
|
||||
{
|
||||
try
|
||||
{
|
||||
return (T) _storage[key];
|
||||
}
|
||||
catch
|
||||
{
|
||||
return default;
|
||||
}
|
||||
}
|
||||
|
||||
public void Set<T>(string key, T value)
|
||||
{
|
||||
_storage.Remove(key);
|
||||
_storage.Add(key, value);
|
||||
}
|
||||
|
||||
public void Remove(string key)
|
||||
{
|
||||
_storage.Remove(key);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -7,8 +7,9 @@ namespace Geekbot.net.Lib.ReactionListener
|
|||
public interface IReactionListener
|
||||
{
|
||||
bool IsListener(ulong id);
|
||||
Task AddRoleToListener(string messageId, IEmote emoji, IRole role);
|
||||
Task AddRoleToListener(ulong messageId, ulong guildId, string emoji, IRole role);
|
||||
void RemoveRole(ISocketMessageChannel channel, SocketReaction reaction);
|
||||
void GiveRole(ISocketMessageChannel message, SocketReaction reaction);
|
||||
IEmote ConvertStringToEmote(string emoji);
|
||||
}
|
||||
}
|
|
@ -1,80 +1,66 @@
|
|||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Discord;
|
||||
using Discord.WebSocket;
|
||||
using StackExchange.Redis;
|
||||
using Geekbot.net.Database;
|
||||
using Geekbot.net.Database.Models;
|
||||
using Geekbot.net.Lib.Extensions;
|
||||
|
||||
namespace Geekbot.net.Lib.ReactionListener
|
||||
{
|
||||
public class ReactionListener : IReactionListener
|
||||
{
|
||||
private readonly IDatabase _redis;
|
||||
private Dictionary<string, Dictionary<IEmote, ulong>> _listener;
|
||||
private readonly DatabaseContext _database;
|
||||
private Dictionary<ulong, Dictionary<IEmote, ulong>> _listener;
|
||||
|
||||
public ReactionListener(IDatabase redis)
|
||||
public ReactionListener(DatabaseContext database)
|
||||
{
|
||||
_redis = redis;
|
||||
_database = database;
|
||||
LoadListeners();
|
||||
}
|
||||
|
||||
private void LoadListeners()
|
||||
{
|
||||
var ids = _redis.SetMembers("MessageIds");
|
||||
_listener = new Dictionary<string, Dictionary<IEmote, ulong>>();
|
||||
foreach (var id in ids)
|
||||
_listener = new Dictionary<ulong, Dictionary<IEmote, ulong>>();
|
||||
foreach (var row in _database.ReactionListeners)
|
||||
{
|
||||
var reactions = _redis.HashGetAll($"Messages:{id}");
|
||||
var messageId = id;
|
||||
var emojiDict = new Dictionary<IEmote, ulong>();
|
||||
foreach (var r in reactions)
|
||||
var messageId = row.MessageId.AsUlong();
|
||||
if (!_listener.ContainsKey(messageId))
|
||||
{
|
||||
IEmote emote;
|
||||
if (!r.Name.ToString().StartsWith('<'))
|
||||
{
|
||||
var emo = new Emoji(r.Name);
|
||||
emote = emo;
|
||||
_listener.Add(messageId, new Dictionary<IEmote, ulong>());
|
||||
}
|
||||
else
|
||||
{
|
||||
emote = Emote.Parse(r.Name);
|
||||
}
|
||||
emojiDict.Add(emote, ulong.Parse(r.Value));
|
||||
}
|
||||
_listener.Add(messageId, emojiDict);
|
||||
|
||||
_listener[messageId].Add(ConvertStringToEmote(row.Reaction), row.RoleId.AsUlong());
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsListener(ulong id)
|
||||
{
|
||||
return _listener.ContainsKey(id.ToString());
|
||||
return _listener.ContainsKey(id);
|
||||
}
|
||||
|
||||
public Task AddRoleToListener(string messageId, IEmote emoji, IRole role)
|
||||
public async Task AddRoleToListener(ulong messageId, ulong guildId, string emoji, IRole role)
|
||||
{
|
||||
if (_redis.SetMembers("MessageIds").All(e => e.ToString() != messageId))
|
||||
{
|
||||
_redis.SetAdd("MessageIds", messageId);
|
||||
}
|
||||
_redis.HashSet($"Messages:{messageId}", new[] {new HashEntry(emoji.ToString(), role.Id.ToString())});
|
||||
_redis.SetAdd("MessageIds", messageId);
|
||||
if (_listener.ContainsKey(messageId))
|
||||
{
|
||||
_listener[messageId].Add(emoji, role.Id);
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
var emote = ConvertStringToEmote(emoji);
|
||||
|
||||
var dict = new Dictionary<IEmote, ulong>
|
||||
await _database.ReactionListeners.AddAsync(new ReactionListenerModel()
|
||||
{
|
||||
{emoji, role.Id}
|
||||
};
|
||||
_listener.Add(messageId, dict);
|
||||
return Task.CompletedTask;
|
||||
GuildId = guildId.AsLong(),
|
||||
MessageId = messageId.AsLong(),
|
||||
RoleId = role.Id.AsLong(),
|
||||
Reaction = emoji
|
||||
});
|
||||
|
||||
if (!_listener.ContainsKey(messageId))
|
||||
{
|
||||
_listener.Add(messageId, new Dictionary<IEmote, ulong>());
|
||||
}
|
||||
_listener[messageId].Add(emote, role.Id);
|
||||
}
|
||||
|
||||
public async void RemoveRole(ISocketMessageChannel channel, SocketReaction reaction)
|
||||
{
|
||||
var roleId = _listener[reaction.MessageId.ToString()][reaction.Emote];
|
||||
var roleId = _listener[reaction.MessageId][reaction.Emote];
|
||||
var guild = (SocketGuildChannel) channel;
|
||||
var role = guild.Guild.GetRole(roleId);
|
||||
await ((IGuildUser) reaction.User.Value).RemoveRoleAsync(role);
|
||||
|
@ -82,10 +68,19 @@ namespace Geekbot.net.Lib.ReactionListener
|
|||
|
||||
public async void GiveRole(ISocketMessageChannel channel, SocketReaction reaction)
|
||||
{
|
||||
var roleId = _listener[reaction.MessageId.ToString()][reaction.Emote];
|
||||
var roleId = _listener[reaction.MessageId][reaction.Emote];
|
||||
var guild = (SocketGuildChannel) channel;
|
||||
var role = guild.Guild.GetRole(roleId);
|
||||
await ((IGuildUser) reaction.User.Value).AddRoleAsync(role);
|
||||
}
|
||||
|
||||
public IEmote ConvertStringToEmote(string emoji)
|
||||
{
|
||||
if (!emoji.StartsWith('<'))
|
||||
{
|
||||
return new Emoji(emoji);
|
||||
}
|
||||
return Emote.Parse(emoji);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -14,6 +14,7 @@ using Geekbot.net.Lib.Converters;
|
|||
using Geekbot.net.Lib.ErrorHandling;
|
||||
using Geekbot.net.Lib.GlobalSettings;
|
||||
using Geekbot.net.Lib.Highscores;
|
||||
using Geekbot.net.Lib.KvInMemoryStore;
|
||||
using Geekbot.net.Lib.Levels;
|
||||
using Geekbot.net.Lib.Localization;
|
||||
using Geekbot.net.Lib.Logger;
|
||||
|
@ -125,6 +126,7 @@ namespace Geekbot.net
|
|||
var mtgManaConverter = new MtgManaConverter();
|
||||
var wikipediaClient = new WikipediaClient();
|
||||
var randomNumberGenerator = new RandomNumberGenerator();
|
||||
var kvMemoryStore = new KvInInMemoryStore();
|
||||
|
||||
_services.AddSingleton(_redis);
|
||||
_services.AddSingleton(_userRepository);
|
||||
|
@ -137,6 +139,7 @@ namespace Geekbot.net
|
|||
_services.AddSingleton<IMtgManaConverter>(mtgManaConverter);
|
||||
_services.AddSingleton<IWikipediaClient>(wikipediaClient);
|
||||
_services.AddSingleton<IRandomNumberGenerator>(randomNumberGenerator);
|
||||
_services.AddSingleton<IKvInMemoryStore>(kvMemoryStore);
|
||||
_services.AddSingleton(_globalSettings);
|
||||
_services.AddTransient<IHighscoreManager>(e => new HighscoreManager(_databaseInitializer.Initialize(), _userRepository));
|
||||
_services.AddTransient(e => _databaseInitializer.Initialize());
|
||||
|
@ -164,7 +167,7 @@ namespace Geekbot.net
|
|||
_logger.Information(LogSource.Geekbot, "Registering Stuff");
|
||||
var translationHandler = new TranslationHandler(_databaseInitializer.Initialize(), _logger);
|
||||
var errorHandler = new ErrorHandler(_logger, translationHandler, _runParameters.ExposeErrors);
|
||||
var reactionListener = new ReactionListener(_redis.Db);
|
||||
var reactionListener = new ReactionListener(_databaseInitializer.Initialize());
|
||||
_services.AddSingleton<IErrorHandler>(errorHandler);
|
||||
_services.AddSingleton<ITranslationHandler>(translationHandler);
|
||||
_services.AddSingleton(_client);
|
||||
|
|
Loading…
Reference in a new issue