public async Task ScheduleRequiresMultipleEmbeds() { const int teamsCount = 50; const int readersCount = teamsCount / 2; MessageStore messageStore = new MessageStore(); ICommandContext context = this.CreateCommandContext(messageStore, guildId: DefaultGuildId); GlobalTournamentsManager globalManager = new GlobalTournamentsManager(); TournamentsManager manager = globalManager.GetOrAdd(DefaultGuildId, id => new TournamentsManager()); HashSet <Team> teams = new HashSet <Team>( Enumerable.Range(1, teamsCount).Select(id => new Team() { Name = $"#Team{id}" })); HashSet <Reader> readers = new HashSet <Reader>( Enumerable.Range(1, readersCount).Select(id => new Reader() { Id = (ulong)id, Name = $"#Reader{id}" })); RoundRobinScheduleFactory factory = new RoundRobinScheduleFactory(1, 0); Schedule schedule = factory.Generate(teams, readers); ITournamentState state = new TournamentState(DefaultGuildId, "T"); state.Schedule = schedule; manager.AddOrUpdateTournament(state.Name, state, (name, oldState) => oldState); Assert.IsTrue( manager.TrySetCurrentTournament(state.Name, out string errorMessage), $"Failed to set the tournament: '{errorMessage}'"); globalManager.GetOrAdd(DefaultGuildId, id => manager); BotCommandHandler commandHandler = new BotCommandHandler(context, globalManager); await commandHandler.GetScheduleAsync(); Assert.IsTrue( messageStore.ChannelEmbeds.Count > 1, $"Expected more than 1 embed, got {messageStore.ChannelEmbeds.Count}"); string allEmbeds = string.Join('\n', messageStore.ChannelEmbeds); for (int round = 0; round < schedule.Rounds.Count; round++) { Assert.IsTrue( allEmbeds.Contains(BotStrings.RoundNumber(round + 1)), $"Round {round + 1} not found in the embeds. Embeds: '{allEmbeds}'"); foreach (Game game in schedule.Rounds[round].Games) { string expectedGame = BotStrings.ScheduleLine( game.Reader.Name, game.Teams.Select(team => team.Name).ToArray()); Assert.IsTrue( allEmbeds.Contains(expectedGame), $"Game '{expectedGame}' not foudn in embed. Embed: '{allEmbeds}'"); } } }
public override Task <PreconditionResult> CheckPermissionsAsync( ICommandContext context, CommandInfo command, IServiceProvider serviceProvider) { Verify.IsNotNull(context, nameof(context)); GlobalTournamentsManager globalManager = serviceProvider.GetService <GlobalTournamentsManager>(); TournamentsManager manager = globalManager.GetOrAdd(context.Guild.Id, CreateTournamentsManager); // TD is only allowed to run commands when they are a director of the current tournament. Result <bool> result = manager.TryReadActionOnCurrentTournament(currentTournament => currentTournament.GuildId == context.Guild.Id && CanActAsTournamentDirector(context, currentTournament) ); if (result.Success && result.Value) { return(Task.FromResult(PreconditionResult.FromSuccess())); } else if (command.Name == SetupCommandName && context.Message.Content.Length > SetupCommand.Length) { // TODO: We should investigate if there's a better place to make this check, because the attribute // now knows about "setup" string tournamentName = context.Message.Content.Substring(SetupCommand.Length).Trim(); if (IsAdminUser(context) || (manager.TryGetTournament(tournamentName, out ITournamentState tournament) && CanActAsTournamentDirector(context, tournament))) { return(Task.FromResult(PreconditionResult.FromSuccess())); } } return(Task.FromResult(PreconditionResult.FromError("User did not have tournament director privileges."))); }
public async Task AddTwoTournamentDirectors() { const ulong firstUserId = 123; const ulong secondUserId = 1234; MessageStore messageStore = new MessageStore(); ICommandContext context = this.CreateCommandContext(messageStore); GlobalTournamentsManager globalManager = new GlobalTournamentsManager(); AddTournamentDirectorDirectly(globalManager, firstUserId); BotCommandHandler commandHandler = new BotCommandHandler(context, globalManager); IGuildUser guildUser = this.CreateGuildUser(secondUserId); await commandHandler.AddTournamentDirectorAsync(guildUser, DefaultTournamentName); string expectedMessage = BotStrings.AddTournamentDirectorSuccessful( DefaultTournamentName, DefaultGuildName); messageStore.VerifyChannelMessages(expectedMessage); TournamentsManager manager = globalManager.GetOrAdd(DefaultGuildId, id => new TournamentsManager()); Assert.IsTrue( manager.TryGetTournament(DefaultTournamentName, out ITournamentState state), "Could not find tournament."); Assert.IsTrue(state.IsDirector(firstUserId), "First director was not added."); Assert.IsTrue(state.IsDirector(secondUserId), "Second director was not added."); }
protected ITournamentState AddCurrentTournament( GlobalTournamentsManager globalManager, ulong guildId = DefaultGuildId, string tournamentName = DefaultTournamentName) { TournamentsManager manager = globalManager.GetOrAdd(guildId, id => new TournamentsManager()); ITournamentState state = new TournamentState(guildId, tournamentName); state = manager.AddOrUpdateTournament(tournamentName, state, (name, oldState) => state); Assert.IsTrue( manager.TrySetCurrentTournament(tournamentName, out string errorMessage), "We should be able to set the current tournament."); return(state); }
// TODO: Add test for ClearAll that checks that all artifacts are cleared. private static void AddTournamentDirectorDirectly(GlobalTournamentsManager globalManager, ulong userId) { TournamentsManager manager = globalManager.GetOrAdd( DefaultGuildId, id => new TournamentsManager() { GuildId = id }); ITournamentState state = manager.AddOrUpdateTournament( DefaultTournamentName, new TournamentState(DefaultGuildId, DefaultTournamentName), (name, oldState) => oldState); Assert.IsTrue(state.TryAddDirector(userId), "First TD added should occur."); }
public async Task RemoveNonexistentTournamentDirector() { const ulong otherId = DefaultUserId + 1; MessageStore messageStore = new MessageStore(); ICommandContext context = this.CreateCommandContext(messageStore); GlobalTournamentsManager globalManager = new GlobalTournamentsManager(); BotCommandHandler commandHandler = new BotCommandHandler(context, globalManager); AddTournamentDirectorDirectly(globalManager, DefaultUserId); IGuildUser guildUser = this.CreateGuildUser(otherId); await commandHandler.RemoveTournamentDirectorAsync(guildUser, DefaultTournamentName); string expectedMessage = BotStrings.UserNotTournamentDirector(DefaultTournamentName, DefaultGuildName); messageStore.VerifyChannelMessages(expectedMessage); TournamentsManager manager = globalManager.GetOrAdd(DefaultGuildId, id => new TournamentsManager()); Assert.IsTrue( manager.TryGetTournament(DefaultTournamentName, out ITournamentState state), "Could not find tournament."); Assert.IsFalse(state.IsDirector(otherId), "Director should not have been added."); }
public async Task AddSameTournamentDirectors() { MessageStore messageStore = new MessageStore(); ICommandContext context = this.CreateCommandContext(messageStore); GlobalTournamentsManager globalManager = new GlobalTournamentsManager(); AddTournamentDirectorDirectly(globalManager, DefaultUserId); BotCommandHandler commandHandler = new BotCommandHandler(context, globalManager); IGuildUser guildUser = this.CreateGuildUser(DefaultUserId); await commandHandler.AddTournamentDirectorAsync(guildUser, DefaultTournamentName); string expectedMessage = BotStrings.UserAlreadyTournamentDirector(DefaultTournamentName, DefaultGuildName); messageStore.VerifyChannelMessages(expectedMessage); TournamentsManager manager = globalManager.GetOrAdd(DefaultGuildId, id => new TournamentsManager()); Assert.IsTrue( manager.TryGetTournament(DefaultTournamentName, out ITournamentState state), "Could not find tournament."); Assert.IsTrue(state.IsDirector(DefaultUserId), "User should still be a director."); }
public async Task SimplestSchedule() { const string readerName = "#Reader"; const string firstTeamName = "#TeamA"; const string secondTeamName = "#TeamB"; MessageStore messageStore = new MessageStore(); ICommandContext context = this.CreateCommandContext(messageStore, guildId: DefaultGuildId); GlobalTournamentsManager globalManager = new GlobalTournamentsManager(); TournamentsManager manager = globalManager.GetOrAdd(DefaultGuildId, id => new TournamentsManager()); HashSet <Team> teams = new HashSet <Team>() { new Team() { Name = firstTeamName }, new Team() { Name = secondTeamName } }; HashSet <Reader> readers = new HashSet <Reader>() { new Reader() { Id = 0, Name = readerName } }; RoundRobinScheduleFactory factory = new RoundRobinScheduleFactory(2, 0); Schedule schedule = factory.Generate(teams, readers); ITournamentState state = new TournamentState(DefaultGuildId, "T"); state.Schedule = schedule; manager.AddOrUpdateTournament(state.Name, state, (name, oldState) => oldState); Assert.IsTrue( manager.TrySetCurrentTournament(state.Name, out string errorMessage), $"Failed to set the tournament: '{errorMessage}'"); globalManager.GetOrAdd(DefaultGuildId, id => manager); BotCommandHandler commandHandler = new BotCommandHandler(context, globalManager); await commandHandler.GetScheduleAsync(); Assert.AreEqual(1, messageStore.ChannelEmbeds.Count, "Unexpected number of embeds"); string embed = messageStore.ChannelEmbeds[0]; for (int round = 0; round < schedule.Rounds.Count; round++) { Assert.IsTrue( embed.Contains(BotStrings.RoundNumber(round + 1)), $"Round {round + 1} not found in embed. Embed: '{embed}'"); string expectedGame = BotStrings.ScheduleLine( readerName, schedule.Rounds[round].Games[0].Teams.Select(team => team.Name).ToArray()); Assert.IsTrue( embed.Contains(expectedGame), $"Game '{expectedGame}' not foudn in embed. Embed: '{embed}'"); } }