diff --git a/src/Discord.Net.Commands/Attributes/AliasAttribute.cs b/src/Discord.Net.Commands/Attributes/AliasAttribute.cs
new file mode 100644
index 000000000..9aa1371f6
--- /dev/null
+++ b/src/Discord.Net.Commands/Attributes/AliasAttribute.cs
@@ -0,0 +1,18 @@
+using System;
+
+namespace Discord.Commands
+{
+ /// Provides aliases for a command.
+ [AttributeUsage(AttributeTargets.Method)]
+ public class AliasAttribute : Attribute
+ {
+ /// The aliases which have been defined for the command.
+ public string[] Aliases { get; }
+
+ /// Creates a new with the given aliases.
+ public AliasAttribute(params string[] aliases)
+ {
+ Aliases = aliases;
+ }
+ }
+}
diff --git a/src/Discord.Net.Commands/Command.cs b/src/Discord.Net.Commands/Command.cs
index 3e8d596dd..f7bbc7d35 100644
--- a/src/Discord.Net.Commands/Command.cs
+++ b/src/Discord.Net.Commands/Command.cs
@@ -25,6 +25,7 @@ namespace Discord.Commands
public string Summary { get; }
public string Text { get; }
public bool HasVarArgs { get; }
+ public IReadOnlyList Aliases { get; }
public IReadOnlyList Parameters { get; }
public IReadOnlyList Preconditions { get; }
@@ -37,6 +38,16 @@ namespace Discord.Commands
Name = source.Name;
Text = groupPrefix + attribute.Text;
+ var aliasesBuilder = ImmutableArray.CreateBuilder();
+
+ aliasesBuilder.Add(Text);
+
+ var aliasesAttr = source.GetCustomAttribute();
+ if (aliasesAttr != null)
+ aliasesBuilder.AddRange(aliasesAttr.Aliases.Select(x => groupPrefix + x));
+
+ Aliases = aliasesBuilder.ToImmutable();
+
var nameAttr = source.GetCustomAttribute();
if (nameAttr != null)
Name = nameAttr.Text;
@@ -81,7 +92,19 @@ namespace Discord.Commands
if (preconditionResult != null && !preconditionResult.Value.IsSuccess)
return ParseResult.FromError(preconditionResult.Value);
- return await CommandParser.ParseArgs(this, msg, searchResult.Text.Substring(Text.Length), 0).ConfigureAwait(false);
+ string input = searchResult.Text;
+ var matchingAliases = Aliases.Where(alias => input.StartsWith(alias));
+
+ string matchingAlias = "";
+ foreach (string alias in matchingAliases)
+ {
+ if (alias.Length > matchingAlias.Length)
+ matchingAlias = alias;
+ }
+
+ input = input.Substring(matchingAlias.Length);
+
+ return await CommandParser.ParseArgs(this, msg, input, 0).ConfigureAwait(false);
}
public Task Execute(IMessage msg, ParseResult parseResult)
{
diff --git a/src/Discord.Net.Commands/Map/CommandMap.cs b/src/Discord.Net.Commands/Map/CommandMap.cs
index 98ff297b0..f75a0f12f 100644
--- a/src/Discord.Net.Commands/Map/CommandMap.cs
+++ b/src/Discord.Net.Commands/Map/CommandMap.cs
@@ -17,40 +17,44 @@ namespace Discord.Commands
public void AddCommand(Command command)
{
- string text = command.Text;
- int nextSpace = NextWhitespace(text);
- string name;
+ foreach (string text in command.Aliases)
+ {
+ int nextSpace = NextWhitespace(text);
+ string name;
- if (nextSpace == -1)
- name = command.Text;
- else
- name = command.Text.Substring(0, nextSpace);
+ if (nextSpace == -1)
+ name = command.Text;
+ else
+ name = command.Text.Substring(0, nextSpace);
- lock (this)
- {
- var nextNode = _nodes.GetOrAdd(name, x => new CommandMapNode(x));
- nextNode.AddCommand(nextSpace == -1 ? "" : text, nextSpace + 1, command);
+ lock (this)
+ {
+ var nextNode = _nodes.GetOrAdd(name, x => new CommandMapNode(x));
+ nextNode.AddCommand(nextSpace == -1 ? "" : text, nextSpace + 1, command);
+ }
}
}
public void RemoveCommand(Command command)
{
- string text = command.Text;
- int nextSpace = NextWhitespace(text);
- string name;
+ foreach (string text in command.Aliases)
+ {
+ int nextSpace = NextWhitespace(text);
+ string name;
- if (nextSpace == -1)
- name = command.Text;
- else
- name = command.Text.Substring(0, nextSpace);
+ if (nextSpace == -1)
+ name = command.Text;
+ else
+ name = command.Text.Substring(0, nextSpace);
- lock (this)
- {
- CommandMapNode nextNode;
- if (_nodes.TryGetValue(name, out nextNode))
+ lock (this)
{
- nextNode.AddCommand(nextSpace == -1 ? "" : text, nextSpace + 1, command);
- if (nextNode.IsEmpty)
- _nodes.TryRemove(name, out nextNode);
+ CommandMapNode nextNode;
+ if (_nodes.TryGetValue(name, out nextNode))
+ {
+ nextNode.RemoveCommand(nextSpace == -1 ? "" : text, nextSpace + 1, command);
+ if (nextNode.IsEmpty)
+ _nodes.TryRemove(name, out nextNode);
+ }
}
}
}