Exemple #1
0
        public static void ViewHelpInformations(string commandName)
        {
            ConsoleCommand command = ConsoleCommandHandler.GetConsoleCommand(commandName);

            // Not command found -> message & return.
            if (command == null)
            {
                ConsoleOutput.WriteLine(ConsoleType.Help,
                                        $"No console command found for ~w~{commandName}~;~.");
                return;
            }

            // Show command help
            string commandParameter = string.Join(", ", command.MethodInfo.GetParameters()
                                                  .Select(info => $"~m~{info.ParameterType}~;~ {info.Name} " +
                                                          $"~l~{(info.IsOptional ? $" = [{info.DefaultValue}] " : "")}~;~"));

            ConsoleOutput.WriteLine(ConsoleType.Help,
                                    $"Command: ~w~{command.Command}~;~\n" +
                                    $"Aliase: ~w~{string.Join(", ", command.CommandAliases)}\n" +
                                    $"Usage: ~w~{command.Command} {commandParameter}");
        }
        /// <summary>
        ///     Adding new command to the existings commands.
        ///     Checks all command attributes, and give warns on duplicates.
        /// </summary>
        /// <param name="newCommand">The new command</param>
        /// <returns>true if new command is unique, else false (with console message)</returns>
        internal static bool AddToCommands(ConsoleCommand newCommand)
        {
            bool   returnValue = true;
            string oldPrefix   = ConsoleOutput.GetPrefix();

            ConsoleOutput.SetPrefix(oldPrefix.Replace("> ", "\t"));
            try
            {
                // Already used command string -> message
                ConsoleCommand blockingCommand = Commands.FirstOrDefault(cmd =>
                                                                         cmd.Command.ToLower() == newCommand.Command.ToLower());

                if (blockingCommand != null)
                {
                    ConsoleOutput.WriteLine(ConsoleType.Warn,
                                            $"Command duplicate: ~c~{blockingCommand.FullName()}");
                    returnValue = false;
                }

                // Already used alias command string -> message
                blockingCommand = Commands.FirstOrDefault(cmd => cmd.CommandAliases.Contains(newCommand.Command) ||
                                                          cmd.CommandAliases.Any(sa => newCommand.CommandAliases
                                                                                 .Select(s => s.ToLower()).Contains(sa)));
                if (blockingCommand != null)
                {
                    ConsoleOutput.WriteLine(ConsoleType.Warn,
                                            $"Alias duplicate: ~c~{blockingCommand.FullName()}");
                    returnValue = false;
                }

                Commands.Add(newCommand);
                return(returnValue);
            }
            finally
            {
                ConsoleOutput.SetPrefix(oldPrefix);
            }
        }
        /// <summary>
        ///     Inspects a class for Commands.
        /// </summary>
        /// <param name="moduleInstance">The instance of the module wich should be inspected.</param>
        internal static void InspectModule(object moduleInstance)
        {
            List <ConsoleCommand> validCommands   = new List <ConsoleCommand>();
            List <ConsoleCommand> invalidCommands = new List <ConsoleCommand>();

            // Parse commands direct in module
            ParseCommands(moduleInstance);

            // Parse all field & Property infos
            foreach (FieldInfo fieldInfo in moduleInstance.GetType().GetFields())
            {
                ParseMemberInfo(null, fieldInfo, moduleInstance);
            }

            foreach (PropertyInfo propertyInfo in moduleInstance.GetType().GetProperties())
            {
                ParseMemberInfo(propertyInfo, null, moduleInstance);
            }

            // Parse static commands
            ParseStaticCommands();

            // Check for invalid commands & write message if given
            ParseInvalidCommands();
            if (invalidCommands.Any())
            {
                ConsoleOutput.SetPrefix(ConsoleOutput.GetPrefix().Replace(">", "~r~!"));

                foreach (ConsoleCommand invalidCommand in invalidCommands)
                {
                    ConsoleOutput.WriteLine(ConsoleType.ConsoleCommand,
                                            "~r~" + invalidCommand.Command + "~c~ " + invalidCommand.FullName());
                }

                ConsoleOutput.SetPrefix(ConsoleOutput.GetPrefix().Replace("~r~!", ">"));
            }

            // Register commands
            if (validCommands.Any())
            {
                foreach (ConsoleCommand command in validCommands)
                {
                    if (AddToCommands(command)) // On working command
                    {
                        ConsoleOutput.SetPrefix(ConsoleOutput.GetPrefix().Replace(">", "~g~+"));

                        // Highlight important commands
                        string commandColorCode = command.ImportantCommand ? "~#f66e00~" : "~g~";
                        // Command aliases
                        string aliasString =
                            $"{(command.CommandAliases.Any() ? $"~w~({commandColorCode}" : "")}{string.Join($"~w~, {commandColorCode}", command.CommandAliases)}{(command.CommandAliases.Any() ? "~w~)" : "")}";

                        ConsoleOutput.WriteLine(ConsoleType.ConsoleCommand,
                                                $"{commandColorCode}{command.Command} {aliasString} ~c~{command.FullName()}");

                        // Description
                        if (!string.IsNullOrEmpty(command.Description))
                        {
                            string currentPrefix = ConsoleOutput.GetPrefix();
                            ConsoleOutput.SetPrefix("\t\t~c~ > ~;~");
                            ConsoleOutput.WriteLine(ConsoleType.ConsoleCommand, command.Description);
                            ConsoleOutput.SetPrefix(currentPrefix);
                        }
                    }
                    else // on warnings
                    {
                        ConsoleOutput.SetPrefix(ConsoleOutput.GetPrefix().Replace(">", "~o~?"));
                        ConsoleOutput.WriteLine(ConsoleType.ConsoleCommand,
                                                "~o~" + command.Command + "~c~ " + command.FullName());
                    }

                    ConsoleOutput.SetPrefix(ConsoleOutput.GetPrefix().Replace("~g~+", ">").Replace("~o~?", ">"));
                }
            }

            void ParseInvalidCommands()
            {
                foreach (Type type in moduleInstance.GetType().Assembly.GetTypes())
                {
                    foreach (MethodInfo methodInfo in type.GetMethods())
                    {
                        object[] attributes = methodInfo.GetCustomAttributes(typeof(ConsoleCommand), true);

                        if (attributes.Length <= 0)
                        {
                            continue;
                        }

                        foreach (object commandObject in attributes)
                        {
                            // Method is registered as valid -> next.
                            if (validCommands.Any(cmd => cmd.MethodInfo == methodInfo))
                            {
                                continue;
                            }

                            ConsoleCommand command = (ConsoleCommand)commandObject;

                            // Save MethodInfo and Class instance
                            command.MethodInfo = methodInfo;
                            invalidCommands.Add(command);
                        }
                    }
                }
            }

            void ParseStaticCommands()
            {
                foreach (Type type in moduleInstance.GetType().Assembly.GetTypes())
                {
                    foreach (MethodInfo methodInfo in type.GetMethods()
                             .Where(info => info.IsStatic && info.IsPublic && !info.IsConstructor))
                    {
                        object[] attributes = methodInfo.GetCustomAttributes(typeof(ConsoleCommand), true);

                        if (attributes.Length <= 0)
                        {
                            continue;
                        }

                        foreach (object commandObject in attributes)
                        {
                            ConsoleCommand command = (ConsoleCommand)commandObject;

                            // Save MethodInfo and Class instance
                            command.MethodInfo    = methodInfo;
                            command.ClassInstance = null;
                            validCommands.Add(command);
                        }
                    }
                }
            }

            void ParseCommands(object instance)
            {
                foreach (MethodInfo methodInfo in instance.GetType().GetMethods()
                         .Where(info => !info.IsStatic && info.IsPublic && !info.IsConstructor))
                {
                    object[] attributes = methodInfo.GetCustomAttributes(typeof(ConsoleCommand), true);

                    if (attributes.Length <= 0)
                    {
                        continue;
                    }

                    foreach (object commandObject in attributes)
                    {
                        ConsoleCommand command = (ConsoleCommand)commandObject;

                        // Save MethodInfo and Class instance
                        command.MethodInfo    = methodInfo;
                        command.ClassInstance = instance;
                        validCommands.Add(command);
                    }
                }
            }

            void ParseMemberInfo(PropertyInfo propertyInfo, FieldInfo fieldInfo, object classInstance)
            {
                object instance = propertyInfo?.GetValue(classInstance) ?? fieldInfo?.GetValue(classInstance);

                if (instance == null ||
                    instance.GetType().Assembly != moduleInstance.GetType().Assembly || !instance.GetType().IsClass)
                {
                    return;
                }

                // Search for commands
                ParseCommands(instance);
                foreach (FieldInfo field in instance.GetType().GetFields())
                {
                    ParseMemberInfo(null, field, instance);
                }

                foreach (PropertyInfo property in instance.GetType().GetProperties())
                {
                    ParseMemberInfo(property, null, instance);
                }
            }
        }