Simple Command system Below I have coded a simple command system that passes a string to a method and checks if the first word split by (' ') is a key in the registered commands dictionary, if it is, it executes the class that is stored as the dictionary entry's value.

few examles of what is typed for commands

@mycommand hello
:ohnicecommand John
.setamount 10000


CommandHandler.cs:

using System;
using System.Collections.Generic;

namespace Sirius.Base.Game.Habbo.Commands
{
    using Commands;
    using Commands.Habbo;
    using Other.GameClients;

    internal class CommandHandler
    {
        private readonly Dictionary&lt;string, ICommand&gt; _commandsRegistered;

        internal CommandHandler()
        {
            _commandsRegistered = new Dictionary&lt;string, ICommand&gt;();

            RegisterCommands();
        }

        private void RegisterCommands()
        {
            RegisterCommand(":info", new InfoCommand());
        }

        public bool IsCommandInput(Player player, string input)
        {
            ICommand command;

            var cmdString = input.Split(' ')[0];

            if (!_commandsRegistered.TryGetValue(cmdString, out command))
            {
                return false;
            }

            if (command.PermissionRequired != "" &amp;&amp; !player.GetPlayerData().GetPermissions().HasCommand(command.PermissionRequired))
            {
                return false;
            }

            if (command.NumberOfParameters &lt; input.Split(' ').Length)
            {
                player.SendWhisper("Invalid command syntax -- " + cmdString + " " + command.CommandParameters);
                return true;
            }

            DateTime lastExecuted;

            if (player.GetPlayerData()._commandCooldowns.TryGetValue(cmdString, out lastExecuted))
            {
                var commandSpan = DateTime.Now - lastExecuted;

                if (command.CommandCooldown &amp;&amp; commandSpan.TotalSeconds &lt; (command.CommandCooldownMs / 1000))
                {
                    player.SendNotification("You're cooling down from this command! [" + commandSpan.TotalSeconds + "/" + (command.CommandCooldownMs / 1000) + "]");
                    return true;
                }
            }
            else
            {
                player.GetPlayerData()._commandCooldowns.Add(cmdString, DateTime.Now);
            }

            command.ProcessCommand(player);

            return true;
        }

        private void RegisterCommand(string commandName, ICommand command)
        {
            _commandsRegistered.Add(commandName, command);
        }
    }
}


ICommand:

namespace Sirius.Base.Game.Habbo.Commands.Commands
{
    using Other.GameClients;

    internal interface ICommand
    {
        void ProcessCommand(Player player);
        string PermissionRequired { get; }
        int NumberOfParameters { get; }
        string CommandParameters { get; }
        string CommandDescription { get; }
        bool CommandCooldown { get; }
        int CommandCooldownMs { get; }
    }
}


InfoCommand (just 1 of many commands)

using System;
using System.Text;

namespace Sirius.Base.Game.Habbo.Commands.Commands.Habbo
{
    using Other.Communication.Packets.Outgoing.Notifications;
    using Other.GameClients;

    internal sealed class InfoCommand : ICommand
    {
        public string PermissionRequired =&gt; "";
        public int NumberOfParameters =&gt; 0;
        public string CommandParameters =&gt; "";
        public string CommandDescription =&gt; "Lets you view information about the server.";
        public bool CommandCooldown =&gt; true;
        public int CommandCooldownMs =&gt; 5000;

        public void ProcessCommand(Player player)
        {
            // do what ever you want the command to do here...
        }
    }
}
The biggest issue I see is you have to manually register each and every command. Why bother? Why not just get a list of all commands that implement ICommand through Reflection? Speed shouldn't be a huge problem because I assume you do this on some sort of start-up.

var baseCommandInterface = typeof(ICommand);
var commands = AppDomain.CurrentDomain.GetAssemblies()
    .SelectMany(s =&gt; s.GetTypes())
    .Where(p =&gt; baseCommandInterface.IsAssignableFrom(p));


Now just enumerate commands and cast and operate on them. Life should be a lot easier this way.



Next, why bother with a bool and int for cool downs? Just use an int?, if it's null then there's no cool down, if its &gt;0 then that's the cool down time. Pretty simple.



You use the term Command way too many times for my tastes.

internal interface ICommand
{
    void Process(Player player);
    string PermissionRequired { get; }
    int NumberOfParameters { get; }
    string Parameters { get; }
    string Description { get; }
    int? CooldownMs { get; }
}


Even then, NumberOfParameters is truly unnecessary. I'd bet there is a separator of some sort between commands in the Parameters string, which really shouldn't be a string, but should be something like the following:

public class CommandParameter
{
    public string Name { get; set; }
    public Type Type { get; set; }
    public string Description { get; set; }
}


Then Parameters becomes an IEnumerable&lt;CommandParameter&gt; which means you can use Parameters.Count in place of NumberOfParameters. This also means you can extrapolate further and define an abstract class for this, and add a CanProcess(Player player) method:

public abstract class BaseCommand : ICommand
{
    private List&lt;CommandParameter&gt; _parameters = new List&lt;CommandParameter&gt;();
    public IEnumerable&lt;CommandParameter&gt; Parameters =&gt; _parameters;

    public int? Cooldown { get; protected set; }
    public string Description { get; protected set; }
    public string PermissionRequired { get; protected set; }

    public abstract void ProcessCommand(Player player);

    public bool CanProcess(Player player)
    {
        // Check cool down, permissions, ban list, etc.
    }
}


Then in an actual command:

public class InfoCommand : BaseCommand
{
    public InfoCommand()
    {
        Cooldown = 5000;
        Description = "Lets you view information about the server.";
    }

    public override void ProcessCommand(Player player)
    {
        if (!CanProcess(player))
        {
            // I'm throwing an exception, but you could just `return` and send a message or whatever
            throw new InvalidOperationException("You have either exceeded the cool down, do not have permissions, or are banned. Please try again later.");
        }

        // Process our command here
    }
}


Then you created your own system that requires boilerplate code, and extracted that boilerplate code away.