Clean all the things!

This commit is contained in:
RogueException
2015-08-26 16:14:19 -03:00
parent a19c4b4547
commit 9d06e2b48d
28 changed files with 238 additions and 355 deletions

View File

@@ -0,0 +1,21 @@
using System;
using System.Threading.Tasks;
namespace Discord.Commands
{
public sealed class Command
{
public string Text { get; }
public int? MinArgs { get; internal set; }
public int? MaxArgs { get; internal set; }
public int MinPerms { get; internal set; }
internal readonly string[] Parts;
internal Func<DiscordBotClient.CommandEventArgs, Task> Handler;
internal Command(string text)
{
Text = text;
Parts = text.ToLowerInvariant().Split(' ');
}
}
}

View File

@@ -1,32 +1,106 @@
using System;
using System.Threading.Tasks;
namespace Discord
namespace Discord.Commands
{
public sealed class CommandBuilder
{
private readonly Command _command;
public CommandBuilder(Command command)
{
_command = command;
}
public CommandBuilder ArgsEqual(int argCount)
{
_command.MinArgs = argCount;
_command.MaxArgs = argCount;
return this;
}
public CommandBuilder ArgsAtLeast(int minArgCount)
{
_command.MinArgs = minArgCount;
_command.MaxArgs = null;
return this;
}
public CommandBuilder ArgsAtMost(int maxArgCount)
{
_command.MinArgs = null;
_command.MaxArgs = maxArgCount;
return this;
}
public CommandBuilder ArgsBetween(int minArgCount, int maxArgCount)
{
_command.MinArgs = minArgCount;
_command.MaxArgs = maxArgCount;
return this;
}
public CommandBuilder NoArgs()
{
_command.MinArgs = 0;
_command.MaxArgs = 0;
return this;
}
public CommandBuilder AnyArgs()
{
_command.MinArgs = null;
_command.MaxArgs = null;
return this;
}
public CommandBuilder MinPermissions(int level)
{
_command.MinPerms = level;
return this;
}
public CommandBuilder Do(Func<DiscordBotClient.CommandEventArgs, Task> func)
{
_command.Handler = func;
return this;
}
public CommandBuilder Do(Action<DiscordBotClient.CommandEventArgs> func)
{
#if DNXCORE50
_command.Handler = e => { func(e); return Task.CompletedTask; };
#else
_command.Handler = e => { func(e); return Task.Delay(0); };
#endif
return this;
}
}
public sealed class CommandGroupBuilder
{
private readonly DiscordBotClient _client;
private readonly string _prefix;
private readonly bool _useWhitelist;
private int _defaultMinPermissions;
public CommandBuilder(DiscordBotClient client, string prefix, bool useWhitelist = false)
internal CommandGroupBuilder(DiscordBotClient client, string prefix, int defaultMinPermissions)
{
_client = client;
_prefix = prefix;
_useWhitelist = useWhitelist;
}
_defaultMinPermissions = defaultMinPermissions;
}
public void AddCommandGroup(string cmd, Action<CommandBuilder> config, bool useWhitelist = false)
public CommandGroupBuilder DefaultMinPermissions(int level)
{
config(new CommandBuilder(_client, _prefix + ' ' + cmd, useWhitelist));
_defaultMinPermissions = level;
return this;
}
public void AddCommand(string cmd, int minArgs, int maxArgs, Action<DiscordBotClient.CommandEventArgs> handler, bool? useWhitelist = null)
public CommandGroupBuilder CreateCommandGroup(string cmd, Action<CommandGroupBuilder> config = null)
{
AddCommand(cmd, minArgs, maxArgs, e => { handler(e); return null; }, useWhitelist);
config(new CommandGroupBuilder(_client, _prefix + ' ' + cmd, _defaultMinPermissions));
return this;
}
public void AddCommand(string cmd, int minArgs, int maxArgs, Func<DiscordBotClient.CommandEventArgs, Task> handler, bool? useWhitelist = null)
public CommandBuilder CreateCommand()
=> CreateCommand("");
public CommandBuilder CreateCommand(string cmd)
{
_client.AddCommand(cmd != "" ? _prefix + ' ' + cmd : _prefix, minArgs, maxArgs, handler, useWhitelist ?? _useWhitelist);
var command = new Command(cmd != "" ? _prefix + ' ' + cmd : _prefix);
command.MinPerms = _defaultMinPermissions;
_client._commands.Add(command);
return new CommandBuilder(command);
}
}
}

View File

@@ -1,6 +1,6 @@
using System.Collections.Generic;
namespace Discord
namespace Discord.Commands
{
public static class CommandParser
{
@@ -119,36 +119,5 @@ namespace Discord
args = argList.ToArray();
return true;
}
public static bool ArgsEqual(string[] args, int expected)
{
return args.Length == expected;
}
public static bool ArgsAtLeast(string[] args, int expected)
{
return args.Length >= expected;
}
public static bool ArgsAtMost(string[] args, int expected)
{
return args.Length <= expected;
}
public static bool ArgsIn(string[] args, params int[] expected)
{
int count = args.Length;
for (int i = 0; i < expected.Length; i++)
{
if (count == expected[i])
return true;
}
return false;
}
public static bool ArgsBetween(string[] args, int min, int max)
{
return args.Length >= min && args.Length <= max;
}
public static bool NoArgs(string[] args, params int[] expected)
{
return args.Length == 0;
}
}
}

View File

@@ -1,14 +1,19 @@
using System;
using Discord.Commands;
using System;
namespace Discord
{
public partial class DiscordBotClient : DiscordClient
{
public class PermissionException : Exception { public PermissionException() : base("User does not have permission to run this command.") { } }
public class CommandEventArgs
{
public readonly Message Message;
public readonly Command Command;
public readonly string[] Args;
public Message Message { get; }
public Command Command { get; }
public string CommandText { get; }
public int? Permissions { get; }
public string[] Args { get; }
public User User => Message.User;
public string UserId => Message.UserId;
@@ -17,18 +22,21 @@ namespace Discord
public Server Server => Message.Channel.Server;
public string ServerId => Message.Channel.ServerId;
public CommandEventArgs(Message message, Command command, string[] args)
public CommandEventArgs(Message message, Command command, string commandText, int? permissions, string[] args)
{
Message = message;
Command = command;
CommandText = commandText;
Permissions = permissions;
Args = args;
}
}
public class CommandErrorEventArgs : CommandEventArgs
{
public readonly Exception Exception;
public CommandErrorEventArgs(Message message, Command command, string[] args, Exception ex)
: base(message, command, args)
public Exception Exception { get; }
public CommandErrorEventArgs(CommandEventArgs baseArgs, Exception ex)
: base(baseArgs.Message, baseArgs.Command, baseArgs.CommandText, baseArgs.Permissions, baseArgs.Args)
{
Exception = ex;
}
@@ -40,11 +48,17 @@ namespace Discord
if (RanCommand != null)
RanCommand(this, args);
}
public event EventHandler<CommandEventArgs> UnknownCommand;
private void RaiseUnknownCommand(CommandEventArgs args)
{
if (UnknownCommand != null)
UnknownCommand(this, args);
}
public event EventHandler<CommandErrorEventArgs> CommandError;
private void RaiseCommandError(Message msg, Command command, string[] args, Exception ex)
private void RaiseCommandError(CommandEventArgs args, Exception ex)
{
if (CommandError != null)
CommandError(this, new CommandErrorEventArgs(msg, command, args, ex));
CommandError(this, new CommandErrorEventArgs(args, ex));
}
}
}

View File

@@ -1,33 +1,13 @@
using System;
using Discord.Commands;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
namespace Discord
{
public sealed class Command
{
public readonly string[] Text;
public readonly int MinArgs, MaxArgs;
public readonly bool UseWhitelist;
internal readonly Func<DiscordBotClient.CommandEventArgs, Task> Handler;
public Command(string[] text, int minArgs, int maxArgs, bool useWhitelist, Func<DiscordBotClient.CommandEventArgs, Task> handler)
{
Text = text;
MinArgs = minArgs;
MaxArgs = maxArgs;
UseWhitelist = useWhitelist;
Handler = handler;
}
}
/// <summary>
/// A Discord.Net client with extensions for handling common bot operations like text commands.
/// </summary>
/// <summary> A Discord.Net client with extensions for handling common bot operations like text commands. </summary>
public partial class DiscordBotClient : DiscordClient
{
private List<Command> _commands;
private List<string> _whitelist;
internal List<Command> _commands;
public IEnumerable<Command> Commands => _commands;
@@ -35,17 +15,15 @@ namespace Discord
public bool UseCommandChar { get; set; }
public bool RequireCommandCharInPublic { get; set; }
public bool RequireCommandCharInPrivate { get; set; }
public bool AlwaysUseWhitelist { get; set; }
public DiscordBotClient()
public DiscordBotClient(DiscordClientConfig config = null, Func<User, int> getPermissions = null)
: base(config)
{
_commands = new List<Command>();
_whitelist = new List<string>();
CommandChar = '~';
RequireCommandCharInPublic = true;
RequireCommandCharInPrivate = true;
AlwaysUseWhitelist = false;
MessageCreated += async (s, e) =>
{
@@ -53,10 +31,6 @@ namespace Discord
if (e.Message.UserId == UserId)
return;
//Check the global whitelist
if (AlwaysUseWhitelist && !_whitelist.Contains(e.Message.UserId))
return;
//Check for the command character
string msg = e.Message.Text;
if (UseCommandChar)
@@ -86,9 +60,9 @@ namespace Discord
continue;
bool isValid = true;
for (int j = 0; j < cmd.Text.Length; j++)
for (int j = 0; j < cmd.Parts.Length; j++)
{
if (!string.Equals(args[j], cmd.Text[j], StringComparison.OrdinalIgnoreCase))
if (!string.Equals(args[j], cmd.Parts[j], StringComparison.OrdinalIgnoreCase))
{
isValid = false;
break;
@@ -97,21 +71,26 @@ namespace Discord
if (!isValid)
continue;
//Check Whitelist
if (cmd.UseWhitelist && !_whitelist.Contains(e.Message.UserId))
continue;
//Check Arg Count
int argCount = args.Length - cmd.Text.Length;
int argCount = args.Length - cmd.Parts.Length;
if (argCount < cmd.MinArgs || argCount > cmd.MaxArgs)
continue;
//Run Command
string[] newArgs = new string[argCount];
//Clean Args
string[] newArgs = new string[argCount];
for (int j = 0; j < newArgs.Length; j++)
newArgs[j] = args[j + cmd.Text.Length];
newArgs[j] = args[j + cmd.Parts.Length];
var eventArgs = new CommandEventArgs(e.Message, cmd, newArgs);
//Check Permissions
int permissions = getPermissions != null ? getPermissions(e.Message.User) : 0;
var eventArgs = new CommandEventArgs(e.Message, cmd, msg, permissions, newArgs);
if (permissions < cmd.MinPerms)
{
RaiseCommandError(eventArgs, new PermissionException());
return;
}
//Run Command
RaiseRanCommand(eventArgs);
try
{
@@ -121,31 +100,20 @@ namespace Discord
}
catch (Exception ex)
{
RaiseCommandError(e.Message, cmd, newArgs, ex);
RaiseCommandError(eventArgs, ex);
}
break;
}
};
}
public void AddCommandGroup(string cmd, Action<CommandBuilder> config, bool useWhitelist = false)
public void CreateCommandGroup(string cmd, Action<CommandGroupBuilder> config = null)
=> config(new CommandGroupBuilder(this, cmd, 0));
public CommandBuilder CreateCommand(string cmd)
{
config(new CommandBuilder(this, cmd, useWhitelist));
}
public void AddCommand(string cmd, int minArgs, int maxArgs, Action<CommandEventArgs> handler, bool useWhitelist = false)
{
AddCommand(cmd, minArgs, maxArgs, e => { handler(e); return null; }, useWhitelist);
}
public void AddCommand(string cmd, int minArgs, int maxArgs, Func<CommandEventArgs, Task> handler, bool useWhitelist = false)
{
_commands.Add(new Command(cmd.Split(' '), minArgs, maxArgs, useWhitelist, handler));
}
public void AddWhitelist(User user)
=> AddWhitelist(user.Id);
public void AddWhitelist(string userId)
{
_whitelist.Add(userId);
var command = new Command(cmd);
_commands.Add(command);
return new CommandBuilder(command);
}
}
}

View File

@@ -1,5 +1,5 @@
{
"version": "0.5.0-*",
"version": "0.6.0-beta1",
"description": "A small Discord.Net extension to make bot creation easier.",
"authors": [ "RogueException" ],
"tags": [ "discord", "discordapp" ],
@@ -13,7 +13,7 @@
"warningsAsErrors": true
},
"dependencies": {
"Discord.Net": "0.5.0"
"Discord.Net": "0.6.0-*"
},
"frameworks": {
"net45": { },