import {
    ActionRowBuilder,
    CommandInteraction,
    StringSelectMenuBuilder,
    ApplicationCommandOptionType,
    ApplicationCommandType,
    StringSelectMenuOptionBuilder,
    SlashCommandBuilder,
    StringSelectMenuInteraction,
    ComponentType,
    APIMessageComponentEmoji,
    ApplicationCommandSubGroup,
    PermissionsBitField,
    Interaction,
    ApplicationCommandOption,
    ApplicationCommandSubCommand
} from "discord.js";
import client from "../utils/client.js";
import EmojiEmbed from "../utils/generateEmojiEmbed.js";
import { LoadingEmbed } from "../utils/defaults.js";
import { capitalize } from "../utils/generateKeyValueList.js";
import { getCommandByName, getCommandMentionByName } from "../utils/getCommandDataByName.js";
import getEmojiByName from "../utils/getEmojiByName.js";

const command = new SlashCommandBuilder().setName("help").setDescription("Shows help for commands");

const styles: Record<string, { emoji: string }> = {
    help: { emoji: "NUCLEUS.LOGO" },
    mod: { emoji: "PUNISH.BAN.RED" },
    nucleus: { emoji: "NUCLEUS.LOGO" },
    privacy: { emoji: "NUCLEUS.LOGO" },
    role: { emoji: "GUILD.ROLES.DELETE" },
    rolemenu: { emoji: "GUILD.ROLES.DELETE" },
    server: { emoji: "GUILD.RED" },
    settings: { emoji: "GUILD.SETTINGS.RED" },
    tag: { emoji: "PUNISH.NICKNAME.RED" },
    tags: { emoji: "PUNISH.NICKNAME.RED" },
    ticket: { emoji: "GUILD.TICKET.CLOSE" },
    user: { emoji: "MEMBER.LEAVE" },
    verify: { emoji: "CONTROL.REDTICK" }
};

const callback = async (interaction: CommandInteraction): Promise<void> => {
    const m = await interaction.reply({ embeds: LoadingEmbed, ephemeral: true, fetchReply: true });
    const commands = client.fetchedCommands;

    let closed = false;
    let currentPath: [string, string, string] = ["", "", ""];
    do {
        const commandRow = new ActionRowBuilder<StringSelectMenuBuilder>().addComponents(
            new StringSelectMenuBuilder()
                .setCustomId("commandRow")
                .setPlaceholder("Select a command")
                .addOptions(
                    ...commands
                        .filter((command) => command.type === ApplicationCommandType.ChatInput)
                        .map((command) => {
                            const builder = new StringSelectMenuOptionBuilder()
                                .setLabel(capitalize(command.name))
                                .setValue(command.name)
                                .setDescription(command.description)
                                .setDefault(currentPath[0] === command.name);
                            if (styles[command.name])
                                builder.setEmoji(
                                    getEmojiByName(styles[command.name]!.emoji, "id") as APIMessageComponentEmoji
                                );
                            return builder;
                        })
                )
        );
        const subcommandGroupRow = new ActionRowBuilder<StringSelectMenuBuilder>().addComponents(
            new StringSelectMenuBuilder().setCustomId("subcommandGroupRow")
        );
        const subcommandRow = new ActionRowBuilder<StringSelectMenuBuilder>().addComponents(
            new StringSelectMenuBuilder().setCustomId("subcommandRow")
        );
        const embed = new EmojiEmbed().setTitle("Help").setStatus("Danger").setEmoji("NUCLEUS.LOGO");

        if (currentPath[0] === "" || currentPath[0] === "help") {
            embed.setDescription(
                `Welcome to Nucleus\n\n` +
                    `Select a command to get started${
                        (interaction.member?.permissions as PermissionsBitField).has("ManageGuild")
                            ? `, or run ${getCommandMentionByName("nucleus/guide")} for commands to set up your server`
                            : ``
                    }\n\n\n` +
                    `Nucleus is fully [open source](https://github.com/clicksminuteper/Nucleus), and all currently free features will remain free forever.\n\n` +
                    `You can invite Nucleus to your server using ${getCommandMentionByName("nucleus/invite")}\n` +
                    `Our support server can be found [here](https://discord.gg/bPaNnxe), and we can be emailed at support@clicks.codes`
            );
        } else {
            const currentData = getCommandByName(
                currentPath.filter((value) => value !== "" && value !== "none").join("/")
            );
            const current = commands.find((command) => command.name === currentPath[0])!;

            let optionString = ``;
            let options: (ApplicationCommandOption & {
                nameLocalized?: string;
                descriptionLocalized?: string;
            })[] = [];
            //options
            if (
                currentPath[1] !== "" &&
                currentPath[1] !== "none" &&
                currentPath[2] !== "" &&
                currentPath[2] !== "none"
            ) {
                const Op = current.options.find(
                    (option) => option.name === currentPath[1]
                )! as ApplicationCommandSubGroup;
                const Op2 = Op.options!.find((option) => option.name === currentPath[2])!;
                options = Op2.options ?? [];
            } else if (currentPath[1] !== "" && currentPath[1] !== "none") {
                let Op = current.options.find((option) => option.name === currentPath[1])!;
                if (Op.type === ApplicationCommandOptionType.SubcommandGroup) {
                    options = [];
                } else {
                    Op = Op as ApplicationCommandSubCommand;
                    options = Op.options ?? [];
                }
            } else {
                options = current.options.filter(
                    (option) =>
                        option.type !== ApplicationCommandOptionType.SubcommandGroup &&
                        option.type !== ApplicationCommandOptionType.Subcommand
                );
            }
            for (const option of options) {
                optionString += `> ${option.name} (${ApplicationCommandOptionType[option.type]})- ${
                    option.description
                }\n`;
            }
            const APICommand =
                client.commands[
                    "commands/" + currentPath.filter((value) => value !== "" && value !== "none").join("/")
                ]![0];
            let allowedToRun = true;
            if (APICommand?.check) {
                allowedToRun = await APICommand.check(interaction as Interaction, true);
            }
            embed.setDescription(
                `${getEmojiByName(styles[currentPath[0]]!.emoji)} **${capitalize(currentData.name)}**\n> ${
                    currentData.mention
                }\n\n` +
                    `> ${currentData.description}\n\n` +
                    (APICommand
                        ? `${getEmojiByName(allowedToRun ? "CONTROL.TICK" : "CONTROL.CROSS")} You ${
                              allowedToRun ? "" : "don't "
                          }` + `have permission to use this command\n\n`
                        : "") +
                    (optionString.length > 0 ? "**Options:**\n" + optionString : "")
            );
            const subcommands = current.options.filter(
                (option) => option.type === ApplicationCommandOptionType.Subcommand
            );
            const subcommandGroups = current.options.filter(
                (option) => option.type === ApplicationCommandOptionType.SubcommandGroup
            );

            if (subcommandGroups.length > 0) {
                subcommandGroupRow.components[0]!.addOptions(
                    new StringSelectMenuOptionBuilder()
                        .setLabel("Select a subcommand")
                        .setValue("none")
                        .setDefault(currentPath[1] === "none"),
                    ...subcommandGroups.map((option) =>
                        new StringSelectMenuOptionBuilder()
                            .setLabel(capitalize(option.name))
                            .setValue(option.name)
                            .setDefault(currentPath[1] === option.name)
                    )
                );
                if (
                    subcommandGroupRow.components[0]!.options.find(
                        (option) => option.data.default && option.data.value !== "none"
                    )
                ) {
                    const subsubcommands =
                        (
                            subcommandGroups.find(
                                (option) => option.name === currentPath[1]
                            )! as ApplicationCommandSubGroup
                        ).options ?? [];
                    subcommandRow.components[0]!.addOptions(
                        new StringSelectMenuOptionBuilder()
                            .setLabel("Select a subcommand")
                            .setValue("none")
                            .setDefault(currentPath[2] === "none"),
                        ...subsubcommands.map((option) =>
                            new StringSelectMenuOptionBuilder()
                                .setLabel(capitalize(option.name))
                                .setValue(option.name)
                                .setDefault(currentPath[2] === option.name)
                        )
                    );
                }
            }
            if (subcommands.length > 0) {
                subcommandGroupRow.components[0]!.addOptions(
                    ...subcommands.map((option) =>
                        new StringSelectMenuOptionBuilder()
                            .setLabel(capitalize(option.name))
                            .setValue(option.name)
                            .setDefault(currentPath[1] === option.name)
                    )
                );
            }
        }

        const cmps = [commandRow];
        if (subcommandGroupRow.components[0]!.options.length > 0) cmps.push(subcommandGroupRow);
        if (subcommandRow.components[0]!.options.length > 0) cmps.push(subcommandRow);

        await interaction.editReply({ embeds: [embed], components: cmps });

        let i: StringSelectMenuInteraction;
        try {
            i = await m.awaitMessageComponent<ComponentType.StringSelect>({
                filter: (newInteraction) => interaction.user.id === newInteraction.user.id,
                time: 300000
            });
        } catch (e) {
            closed = true;
            continue;
        }
        await i.deferUpdate();
        const value = i.values[0]!;
        switch (i.customId) {
            case "commandRow": {
                currentPath = [value, "", ""];
                break;
            }
            case "subcommandGroupRow": {
                currentPath = [currentPath[0], value, ""];
                break;
            }
            case "subcommandRow": {
                currentPath[2] = value;
                break;
            }
        }
    } while (!closed);
};

export { command as command };
export { callback };
