zumito-framework 1.2.17 → 1.2.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. package/dist/ZumitoFramework.d.ts +1 -1
  2. package/dist/ZumitoFramework.js +3 -1
  3. package/dist/definitions/ErrorType.d.ts +2 -1
  4. package/dist/definitions/ErrorType.js +1 -0
  5. package/dist/definitions/FrameworkSettings.d.ts +4 -19
  6. package/dist/definitions/commands/Command.d.ts +8 -12
  7. package/dist/definitions/commands/Command.js +9 -4
  8. package/dist/definitions/commands/CommandBinds.d.ts +6 -0
  9. package/dist/definitions/commands/CommandBinds.js +1 -0
  10. package/dist/definitions/commands/CommandParameters.d.ts +10 -3
  11. package/dist/definitions/parameters/EventParameters.d.ts +6 -0
  12. package/dist/definitions/parameters/ModalSubmitParameters.d.ts +10 -0
  13. package/dist/definitions/parameters/ModalSubmitParameters.js +1 -0
  14. package/dist/definitions/parameters/SelectMenuParameters.d.ts +6 -0
  15. package/dist/definitions/settings/FrameworkSettings.d.ts +24 -0
  16. package/dist/definitions/settings/FrameworkSettings.js +1 -0
  17. package/dist/definitions/settings/InteractionHandlerSettings.d.ts +3 -0
  18. package/dist/definitions/settings/InteractionHandlerSettings.js +1 -0
  19. package/dist/index.d.ts +6 -1
  20. package/dist/index.js +5 -1
  21. package/dist/modules/core/baseModule/events/discord/InteractionCreate.d.ts +4 -3
  22. package/dist/modules/core/baseModule/events/discord/InteractionCreate.js +8 -122
  23. package/dist/modules/core/baseModule/events/discord/MessageCreate.d.ts +7 -0
  24. package/dist/modules/core/baseModule/events/discord/MessageCreate.js +35 -36
  25. package/dist/services/CommandManager.js +16 -9
  26. package/dist/services/CommandParser.d.ts +7 -0
  27. package/dist/services/CommandParser.js +32 -0
  28. package/dist/services/ErrorHandler.d.ts +2 -1
  29. package/dist/services/ErrorHandler.js +69 -7
  30. package/dist/services/InteractionHandler.d.ts +21 -0
  31. package/dist/services/InteractionHandler.js +212 -0
  32. package/dist/services/ServiceContainer.d.ts +9 -1
  33. package/dist/services/ServiceContainer.js +14 -2
  34. package/dist/services/SlashCommandRefresher.d.ts +4 -1
  35. package/dist/services/SlashCommandRefresher.js +67 -50
  36. package/dist/services/TranslationManager.d.ts +1 -0
  37. package/dist/services/TranslationManager.js +12 -0
  38. package/package.json +6 -1
@@ -2,7 +2,7 @@ import { Client, GuildMember, TextChannel } from 'discord.js';
2
2
  import { DatabaseModel } from './definitions/DatabaseModel.js';
3
3
  import { EventEmitter } from "tseep";
4
4
  import { FrameworkEvent } from './definitions/FrameworkEvent.js';
5
- import { FrameworkSettings } from './definitions/FrameworkSettings.js';
5
+ import { FrameworkSettings } from './definitions/settings/FrameworkSettings.js';
6
6
  import { StatusManager } from './services/StatusManager.js';
7
7
  import { TranslationManager } from './services/TranslationManager.js';
8
8
  import { EventManager } from './services/EventManager.js';
@@ -138,6 +138,8 @@ export class ZumitoFramework {
138
138
  this.models = [];
139
139
  this.eventManager = new EventManager();
140
140
  ServiceContainer.addService(TranslationManager, [], true, this.translations);
141
+ ServiceContainer.addService(CommandManager, [], true, this.commands);
142
+ ServiceContainer.addService(EventManager, [], true, this.eventManager);
141
143
  if (settings.logLevel) {
142
144
  console.logLevel = settings.logLevel;
143
145
  }
@@ -247,7 +249,7 @@ export class ZumitoFramework {
247
249
  }
248
250
  const __dirname = url.fileURLToPath(new URL('.', import.meta.url));
249
251
  if (this.settings.bundles && this.settings.bundles.length > 0) {
250
- for (let bundle of this.settings.bundles) {
252
+ for (const bundle of this.settings.bundles) {
251
253
  await this.registerBundle(bundle.path, bundle.options);
252
254
  }
253
255
  }
@@ -1,5 +1,6 @@
1
1
  export declare enum ErrorType {
2
2
  CommandInstance = 1,
3
3
  CommandLoad = 2,
4
- CommandRun = 3
4
+ CommandRun = 3,
5
+ Other = 4
5
6
  }
@@ -3,4 +3,5 @@ export var ErrorType;
3
3
  ErrorType[ErrorType["CommandInstance"] = 1] = "CommandInstance";
4
4
  ErrorType[ErrorType["CommandLoad"] = 2] = "CommandLoad";
5
5
  ErrorType[ErrorType["CommandRun"] = 3] = "CommandRun";
6
+ ErrorType[ErrorType["Other"] = 4] = "Other";
6
7
  })(ErrorType || (ErrorType = {}));
@@ -1,19 +1,4 @@
1
- import { ModuleParameters } from "./parameters/ModuleParameters";
2
- import { StatusManagerOptions } from "./StatusManagerOptions";
3
- export interface FrameworkSettings {
4
- database: any;
5
- logLevel?: number;
6
- debug?: boolean;
7
- discordClientOptions: {
8
- intents?: number;
9
- token: string;
10
- clientId: string;
11
- };
12
- defaultPrefix?: string;
13
- statusOptions?: StatusManagerOptions;
14
- srcMode?: 'multiBundle' | 'monoBundle' | undefined;
15
- bundles?: {
16
- path: string;
17
- options?: ModuleParameters;
18
- }[];
19
- }
1
+ /**
2
+ * @deprecated
3
+ */
4
+ export { FrameworkSettings } from "./settings/FrameworkSettings";
@@ -1,6 +1,6 @@
1
1
  import { CommandArgDefinition } from './CommandArgDefinition.js';
2
- import { CommandParameters } from './CommandParameters.js';
3
- import { SelectMenuParameters } from '../parameters/SelectMenuParameters.js';
2
+ import { CommandParameters, PrefixCommandParameters, SlashCommandParameters } from './CommandParameters.js';
3
+ import { CommandBinds } from './CommandBinds.js';
4
4
  /**
5
5
  * @name Command
6
6
  * @description Base class for all commands
@@ -201,19 +201,15 @@ export declare abstract class Command {
201
201
  * @see {@link CommandType}
202
202
  */
203
203
  type: string;
204
+ parent?: string;
205
+ binds?: CommandBinds;
204
206
  /**
205
207
  * @name execute
206
208
  * @description The function that is executed when the command is called.
207
209
  * @param {CommandParameters} parameters The parameters of the command.
208
- * @param {Message} parameters.message The message that triggered the command.
209
- * @param {CommandInteraction} parameters.interaction The interaction that triggered the command.
210
- * @param {string[]} parameters.args The arguments of the command.
211
- * @param {Client} parameters.client The client.
212
- * @param {Framework} parameters.framework The framework.
213
- * @param {trans} (key: string, options?: any) => string Translation shorthand function.
214
210
  */
215
- abstract execute({ message, interaction, args, client, framework, }: CommandParameters): void;
216
- executePrefixCommand({ message, interaction, args, client, framework, trans, }: CommandParameters): void;
217
- executeSlashCommand({ message, interaction, args, client, framework, trans, }: CommandParameters): void;
218
- abstract selectMenu({ path, interaction, client, framework, trans, }: SelectMenuParameters): void;
211
+ abstract execute(parameters: CommandParameters): Promise<void>;
212
+ executePrefixCommand({ message, args, client, framework, trans, }: PrefixCommandParameters): Promise<void>;
213
+ executeSlashCommand({ interaction, args, client, framework, trans, }: SlashCommandParameters): Promise<void>;
214
+ isSubCommand(): boolean;
219
215
  }
@@ -199,10 +199,15 @@ export class Command {
199
199
  * @see {@link CommandType}
200
200
  */
201
201
  type = CommandType.prefix;
202
- executePrefixCommand({ message, interaction, args, client, framework, trans, }) {
203
- this.execute({ message, interaction, args, client, framework, trans });
202
+ parent;
203
+ binds;
204
+ async executePrefixCommand({ message, args, client, framework, trans, }) {
205
+ await this.execute({ message, args, client, framework, trans });
204
206
  }
205
- executeSlashCommand({ message, interaction, args, client, framework, trans, }) {
206
- this.execute({ message, interaction, args, client, framework, trans });
207
+ async executeSlashCommand({ interaction, args, client, framework, trans, }) {
208
+ await this.execute({ interaction, args, client, framework, trans });
209
+ }
210
+ isSubCommand() {
211
+ return this.parent !== undefined;
207
212
  }
208
213
  }
@@ -0,0 +1,6 @@
1
+ import { ModalSubmitParameters } from '@definitions/parameters/ModalSubmitParameters.js';
2
+ import { SelectMenuParameters } from '../parameters/SelectMenuParameters.js';
3
+ export declare type CommandBinds = {
4
+ selectMenu?: (params: SelectMenuParameters) => Promise<void>;
5
+ modalSubmit?: (params: ModalSubmitParameters) => Promise<void>;
6
+ };
@@ -0,0 +1 @@
1
+ export {};
@@ -8,9 +8,7 @@ import { ZumitoFramework } from '../../ZumitoFramework.js';
8
8
  * @property {interaction} interaction - The interaction that triggered the command.
9
9
  * @property {args} args - The arguments passed to the command.
10
10
  */
11
- export interface CommandParameters {
12
- message?: Message;
13
- interaction?: CommandInteraction;
11
+ export interface BaseCommandParameters {
14
12
  args: Map<string, any>;
15
13
  /**
16
14
  * Discord client instance
@@ -29,3 +27,12 @@ export interface CommandParameters {
29
27
  guildSettings?: any;
30
28
  trans: (key: string, params?: any) => string;
31
29
  }
30
+ export declare type SlashCommandParameters = BaseCommandParameters & {
31
+ interaction: CommandInteraction;
32
+ message?: null;
33
+ };
34
+ export declare type PrefixCommandParameters = BaseCommandParameters & {
35
+ message: Message;
36
+ interaction?: null;
37
+ };
38
+ export declare type CommandParameters = PrefixCommandParameters | SlashCommandParameters;
@@ -3,6 +3,12 @@ import { ZumitoFramework } from '../../ZumitoFramework.js';
3
3
  export interface EventParameters {
4
4
  message?: Message;
5
5
  interaction?: Interaction;
6
+ /**
7
+ * @deprecated
8
+ */
6
9
  client?: Client;
10
+ /**
11
+ * @deprecated
12
+ */
7
13
  framework: ZumitoFramework;
8
14
  }
@@ -0,0 +1,10 @@
1
+ import { ModalSubmitInteraction } from 'discord.js';
2
+ export interface ModalSubmitParameters {
3
+ path: string[];
4
+ interaction: ModalSubmitInteraction;
5
+ /**
6
+ * @deprecated
7
+ */
8
+ guildSettings?: any;
9
+ trans: (key: string, params?: any) => string;
10
+ }
@@ -3,7 +3,13 @@ import { ZumitoFramework } from '../../ZumitoFramework.js';
3
3
  export interface SelectMenuParameters {
4
4
  path: string[];
5
5
  interaction: SelectMenuInteraction;
6
+ /**
7
+ * @deprecated
8
+ */
6
9
  client: Client;
10
+ /**
11
+ * @deprecated
12
+ */
7
13
  framework: ZumitoFramework;
8
14
  guildSettings?: any;
9
15
  trans: (key: string, params?: any) => string;
@@ -0,0 +1,24 @@
1
+ import { ModuleParameters } from "../parameters/ModuleParameters";
2
+ import { StatusManagerOptions } from "../StatusManagerOptions";
3
+ export interface FrameworkSettings {
4
+ database: any;
5
+ logLevel?: number;
6
+ debug?: boolean;
7
+ discordClientOptions: {
8
+ intents?: number;
9
+ token: string;
10
+ clientId: string;
11
+ };
12
+ defaultPrefix?: string;
13
+ statusOptions?: StatusManagerOptions;
14
+ /**
15
+ * Read the ./src folder as multiple modules or unique module
16
+ * This feature is experimental and can disapear anytime
17
+ * @experimental
18
+ */
19
+ srcMode?: 'multiBundle' | 'monoBundle' | undefined;
20
+ bundles?: {
21
+ path: string;
22
+ options?: ModuleParameters;
23
+ }[];
24
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,3 @@
1
+ export declare type InteractionHandlerSettings = {
2
+ disabledHandlers?: ('command' | 'selectMenu' | 'button' | 'modal')[];
3
+ };
package/dist/index.d.ts CHANGED
@@ -27,4 +27,9 @@ import { CommandParser } from './services/CommandParser.js';
27
27
  import { SlashCommandRefresher } from './services/SlashCommandRefresher.js';
28
28
  import { ErrorHandler } from './services/ErrorHandler.js';
29
29
  import { Route, RouteMethod } from './definitions/Route.js';
30
- export { ZumitoFramework, FrameworkSettings, Command, Module, CommandParameters, CommandArguments, FrameworkEvent, Translation, TranslationManager, ApiResponse, SelectMenuParameters, CommandType, CommandArgDefinition, CommandChoiceDefinition, ButtonPressed, ButtonPressedParams, TextFormatter, EmojiFallback, DatabaseConfigLoader, DatabaseModel, PresenceDataRule, RuledPresenceData, StatusManagerOptions, discord, EventParameters, ServiceContainer, GuildDataGetter, SlashCommandRefresher, CommandParser, ErrorHandler, Route, RouteMethod };
30
+ import { InteractionHandler } from './services/InteractionHandler.js';
31
+ import { CommandManager } from './services/CommandManager.js';
32
+ import { ErrorType } from './definitions/ErrorType.js';
33
+ export { ModalSubmitParameters } from './definitions/parameters/ModalSubmitParameters.js';
34
+ export { CommandBinds } from './definitions/commands/CommandBinds.js';
35
+ export { ZumitoFramework, FrameworkSettings, Command, Module, CommandParameters, CommandArguments, FrameworkEvent, Translation, TranslationManager, ApiResponse, SelectMenuParameters, CommandType, CommandArgDefinition, CommandChoiceDefinition, ButtonPressed, ButtonPressedParams, TextFormatter, EmojiFallback, DatabaseConfigLoader, DatabaseModel, PresenceDataRule, RuledPresenceData, StatusManagerOptions, discord, EventParameters, ServiceContainer, GuildDataGetter, SlashCommandRefresher, CommandParser, ErrorHandler, ErrorType, Route, RouteMethod, InteractionHandler, CommandManager };
package/dist/index.js CHANGED
@@ -20,11 +20,15 @@ import { CommandParser } from './services/CommandParser.js';
20
20
  import { SlashCommandRefresher } from './services/SlashCommandRefresher.js';
21
21
  import { ErrorHandler } from './services/ErrorHandler.js';
22
22
  import { Route, RouteMethod } from './definitions/Route.js';
23
+ import { InteractionHandler } from './services/InteractionHandler.js';
24
+ import { CommandManager } from './services/CommandManager.js';
25
+ import { ErrorType } from './definitions/ErrorType.js';
23
26
  ServiceContainer.addService(TextFormatter, []);
24
27
  ServiceContainer.addService(EmojiFallback, [discord.Client.name, TranslationManager.name]);
25
28
  ServiceContainer.addService(GuildDataGetter, [ZumitoFramework.name]);
26
29
  ServiceContainer.addService(MemberPermissionChecker, []);
27
30
  ServiceContainer.addService(CommandParser, []);
28
31
  ServiceContainer.addService(SlashCommandRefresher, [ZumitoFramework.name]);
32
+ ServiceContainer.addService(InteractionHandler, []);
29
33
  ServiceContainer.addService(ErrorHandler, ['ZumitoFramework']);
30
- export { ZumitoFramework, Command, Module, CommandArguments, FrameworkEvent, Translation, TranslationManager, ApiResponse, CommandType, ButtonPressed, TextFormatter, EmojiFallback, DatabaseConfigLoader, DatabaseModel, discord, ServiceContainer, GuildDataGetter, SlashCommandRefresher, CommandParser, ErrorHandler, Route, RouteMethod };
34
+ export { ZumitoFramework, Command, Module, CommandArguments, FrameworkEvent, Translation, TranslationManager, ApiResponse, CommandType, ButtonPressed, TextFormatter, EmojiFallback, DatabaseConfigLoader, DatabaseModel, discord, ServiceContainer, GuildDataGetter, SlashCommandRefresher, CommandParser, ErrorHandler, ErrorType, Route, RouteMethod, InteractionHandler, CommandManager };
@@ -1,9 +1,10 @@
1
- import { Command } from '../../../../../definitions/commands/Command.js';
2
1
  import { EventParameters } from '../../../../../definitions/parameters/EventParameters.js';
3
2
  import { FrameworkEvent } from '../../../../../definitions/FrameworkEvent.js';
3
+ import { InteractionHandler } from '../../../../../services/InteractionHandler.js';
4
4
  export declare class InteractionCreate extends FrameworkEvent {
5
5
  once: boolean;
6
6
  source: string;
7
- execute({ interaction, client, framework, }: EventParameters): Promise<void>;
8
- getTransMethod(commandInstance: Command, framework: any, guildSettings: any): (key: string, params?: any) => any;
7
+ interactionHandler: InteractionHandler;
8
+ constructor();
9
+ execute({ interaction, }: EventParameters): Promise<void>;
9
10
  }
@@ -1,129 +1,15 @@
1
- import { CommandType } from '../../../../../definitions/commands/CommandType.js';
2
1
  import { FrameworkEvent } from '../../../../../definitions/FrameworkEvent.js';
2
+ import { ServiceContainer } from '../../../../../services/ServiceContainer.js';
3
+ import { InteractionHandler } from '../../../../../services/InteractionHandler.js';
3
4
  export class InteractionCreate extends FrameworkEvent {
4
5
  once = false;
5
6
  source = 'discord';
6
- async execute({ interaction, client, framework, }) {
7
- let guildSettings;
8
- if (interaction.guildId) {
9
- guildSettings = await framework.getGuildSettings(interaction.guildId);
10
- }
11
- if (interaction.isCommand()) {
12
- if (!framework.commands.getAll().has(interaction.commandName))
13
- return;
14
- const commandInstance = framework.commands.get(interaction.commandName);
15
- const args = new Map();
16
- commandInstance.args.forEach((arg) => {
17
- const option = interaction.options.get(arg.name);
18
- if (option) {
19
- switch (arg.type) {
20
- case 'user':
21
- args.set(arg.name, option.user);
22
- break;
23
- case 'member':
24
- args.set(arg.name, option.member);
25
- break;
26
- default:
27
- args.set(arg.name, option.value ||
28
- option.user ||
29
- option.role ||
30
- option.channel ||
31
- option.options ||
32
- option.message ||
33
- option.member ||
34
- option.focused ||
35
- option.autocomplete ||
36
- option.attachment);
37
- break;
38
- }
39
- }
40
- });
41
- if (![CommandType.any, CommandType.separated, CommandType.slash,].includes(commandInstance.type))
42
- return;
43
- const trans = this.getTransMethod(commandInstance, framework, guildSettings);
44
- if (commandInstance.type === CommandType.separated ||
45
- commandInstance.type === CommandType.slash) {
46
- await commandInstance.executeSlashCommand({
47
- client, interaction, args, framework, guildSettings, trans,
48
- });
49
- }
50
- else {
51
- await commandInstance.execute({
52
- client, interaction, args, framework, guildSettings, trans,
53
- });
54
- }
55
- }
56
- else if (interaction.isButton()) {
57
- interaction = interaction;
58
- const path = interaction.customId.split('.');
59
- const commandInstance = framework.commands.get(path[0]);
60
- if (!commandInstance)
61
- throw new Error(`Command ${path[0]} not found or button id bad formatted`);
62
- // If the command has impements ButtonPress class then execute the method
63
- if (commandInstance.constructor.prototype.hasOwnProperty('buttonPressed')) {
64
- commandInstance.buttonPressed({
65
- path,
66
- interaction,
67
- client,
68
- framework,
69
- guildSettings,
70
- });
71
- }
72
- }
73
- else if (interaction.isStringSelectMenu()) {
74
- const path = interaction.customId.split('.');
75
- const commandInstance = framework.commands.get(path[0]);
76
- if (!commandInstance)
77
- throw new Error(`Command ${path[0]} not found or select menu id bad formatted`);
78
- const trans = (key, params) => {
79
- if (key.startsWith('$')) {
80
- return framework.translations.get(key.replace('$', ''), guildSettings.lang, params);
81
- }
82
- else {
83
- return framework.translations.get('command.' + commandInstance.name + '.' + key, guildSettings.lang, params);
84
- }
85
- };
86
- if (commandInstance.selectMenu) {
87
- commandInstance.selectMenu({
88
- path,
89
- interaction,
90
- client,
91
- framework,
92
- guildSettings,
93
- trans,
94
- });
95
- }
96
- }
97
- else if (interaction.isModalSubmit()) {
98
- const path = interaction.customId.split('.');
99
- const commandInstance = framework.commands.get(path[0]);
100
- if (!commandInstance) {
101
- throw new Error(`Command ${path[0]} not found or modal id bad formatted`);
102
- }
103
- if (commandInstance.modalSubmit) {
104
- commandInstance.modalSubmit({
105
- path,
106
- interaction,
107
- client,
108
- framework,
109
- guildSettings,
110
- });
111
- }
112
- else {
113
- framework.eventManager.emitEvent('modalSubmit', 'framework', {
114
- path, interaction, client, framework, guildSettings,
115
- });
116
- }
117
- }
7
+ interactionHandler;
8
+ constructor() {
9
+ super();
10
+ this.interactionHandler = ServiceContainer.getService(InteractionHandler);
118
11
  }
119
- getTransMethod(commandInstance, framework, guildSettings) {
120
- return (key, params) => {
121
- if (key.startsWith('$')) {
122
- return framework.translations.get(key.replace('$', ''), guildSettings.lang, params);
123
- }
124
- else {
125
- return framework.translations.get('command.' + commandInstance.name + '.' + key, guildSettings.lang, params);
126
- }
127
- };
12
+ async execute({ interaction, }) {
13
+ await this.interactionHandler.handleInteraction(interaction);
128
14
  }
129
15
  }
@@ -1,9 +1,16 @@
1
1
  import { ActionRowBuilder, EmbedBuilder } from 'discord.js';
2
2
  import { EventParameters } from '../../../../../definitions/parameters/EventParameters.js';
3
3
  import { FrameworkEvent } from '../../../../../definitions/FrameworkEvent.js';
4
+ import { MemberPermissionChecker } from '../../../../../services/MemberPermissionChecker.js';
5
+ import { ZumitoFramework } from '../../../../../ZumitoFramework.js';
6
+ import { GuildDataGetter } from '../../../../../services/GuildDataGetter.js';
4
7
  export declare class MessageCreate extends FrameworkEvent {
5
8
  once: boolean;
6
9
  source: string;
10
+ memberPermissionChecker: MemberPermissionChecker;
11
+ framework: ZumitoFramework;
12
+ guildDataGetter: GuildDataGetter;
13
+ constructor();
7
14
  execute({ message, framework }: EventParameters): Promise<import("discord.js").Message<boolean>>;
8
15
  autocorrect(str: string, words: string[]): any;
9
16
  getErrorEmbed(error: any, parse: any): {
@@ -1,20 +1,33 @@
1
1
  import { ActionRowBuilder, ButtonBuilder, ButtonStyle, ChannelType, EmbedBuilder, PermissionsBitField, } from 'discord.js';
2
2
  import ErrorStackParser from 'error-stack-parser';
3
3
  import { FrameworkEvent } from '../../../../../definitions/FrameworkEvent.js';
4
- import { ZumitoFramework } from '../../../../../ZumitoFramework.js';
5
4
  import leven from 'leven';
6
5
  import path from 'path';
7
- import { InteractionIdGenerator } from '../../../../../services/InteractionIdGenerator.js';
6
+ import { ServiceContainer } from '../../../../../services/ServiceContainer.js';
7
+ import { CommandParser } from '../../../../../services/CommandParser.js';
8
+ import { MemberPermissionChecker } from '../../../../../services/MemberPermissionChecker.js';
9
+ import { ZumitoFramework } from '../../../../../ZumitoFramework.js';
10
+ import { GuildDataGetter } from '../../../../../services/GuildDataGetter.js';
8
11
  export class MessageCreate extends FrameworkEvent {
9
12
  once = false;
10
13
  source = 'discord';
14
+ memberPermissionChecker;
15
+ framework;
16
+ guildDataGetter;
17
+ constructor() {
18
+ super();
19
+ this.memberPermissionChecker = ServiceContainer.getService(MemberPermissionChecker);
20
+ this.framework = ServiceContainer.getService(ZumitoFramework);
21
+ this.guildDataGetter = ServiceContainer.getService(GuildDataGetter);
22
+ }
11
23
  async execute({ message, framework }) {
12
24
  const channel = message.channel;
13
25
  const prefix = framework.settings.defaultPrefix;
14
- const args = ZumitoFramework.splitCommandLine(message.content.slice(prefix.length));
26
+ const args = CommandParser.splitCommandLine(message.content.slice(prefix.length));
15
27
  const command = args.shift().toLowerCase();
16
28
  let commandInstance;
17
29
  if (message.content.startsWith(prefix)) {
30
+ debugger;
18
31
  if (!framework.commands.getAll().has(command)) {
19
32
  const commandNames = Array.from(framework.commands.getAll().keys());
20
33
  const correctedCommand = this.autocorrect(command, commandNames);
@@ -26,18 +39,24 @@ export class MessageCreate extends FrameworkEvent {
26
39
  }
27
40
  }
28
41
  else {
29
- commandInstance = framework.commands.get(command);
42
+ const tmpCmd = framework.commands.get(command);
43
+ if (tmpCmd && !tmpCmd.parent) {
44
+ commandInstance = tmpCmd;
45
+ }
30
46
  }
47
+ commandInstance = Array.from(this.framework.commands.getAll().values()).find((c) => c.name == args.at(0) && c.parent && c.parent == command) || commandInstance;
48
+ if (!commandInstance)
49
+ return;
31
50
  if (message.guild == null && commandInstance.dm == false)
32
51
  return;
33
52
  if (commandInstance.adminOnly ||
34
53
  commandInstance.userPermissions.length > 0) {
35
54
  let denied = false;
36
- if (framework.memberHasPermission(message.member, message.channel, PermissionsBitField.Flags.Administrator) ||
55
+ if (this.memberPermissionChecker.hasPermissionOnChannel(message.member, message.channel, PermissionsBitField.Flags.Administrator) ||
37
56
  message.member.id != message.guild.ownerId) {
38
57
  if (commandInstance.userPermissions.length > 0) {
39
58
  commandInstance.userPermissions.forEach((permission) => {
40
- if (!framework.memberHasPermission(message.member, message.channel, permission)) {
59
+ if (!this.memberPermissionChecker.hasPermissionOnChannel(message.member, message.channel, permission)) {
41
60
  denied = true;
42
61
  }
43
62
  });
@@ -70,37 +89,17 @@ export class MessageCreate extends FrameworkEvent {
70
89
  }
71
90
  }
72
91
  try {
73
- const guildSettings = await framework.getGuildSettings(message.guildId);
74
- const parsedArgs = new Map();
75
- for (let i = 0; i < args.length; i++) {
76
- const arg = args[i];
77
- const type = commandInstance.args[i]?.type;
78
- if (type) {
79
- if (type == 'member' || type == 'user') {
80
- const member = await message.guild.members.cache.get(arg.replace(/[<@!>]/g, ''));
81
- if (member) {
82
- if (type == 'user') {
83
- parsedArgs.set(commandInstance.args[i].name, member.user);
84
- }
85
- else {
86
- parsedArgs.set(commandInstance.args[i].name, member);
87
- }
88
- }
89
- else {
90
- return message.reply({
91
- content: 'Invalid user.',
92
- allowedMentions: {
93
- repliedUser: false,
94
- },
95
- });
96
- }
97
- }
98
- else if (type == 'string') {
99
- parsedArgs.set(commandInstance.args?.[i]?.name || i.toString(), arg);
100
- }
101
- }
92
+ const guildSettings = await this.guildDataGetter.getGuildSettings(message.guildId);
93
+ const parsedArgsResponse = await CommandParser.parseFromSplitedString(args, commandInstance.args, message.guild);
94
+ if (parsedArgsResponse.errors.length > 0) {
95
+ return message.reply({
96
+ content: parsedArgsResponse.errors.at(0),
97
+ allowedMentions: {
98
+ repliedUser: false,
99
+ },
100
+ });
102
101
  }
103
- const interactionIdGenerator = new InteractionIdGenerator(undefined, commandInstance.name);
102
+ const parsedArgs = parsedArgsResponse.parsedArgs;
104
103
  await commandInstance.execute({
105
104
  message,
106
105
  args: parsedArgs,
@@ -40,6 +40,7 @@ export class CommandManager {
40
40
  * @returns {Promise<Command>}
41
41
  */
42
42
  async loadCommandFile(filePath) {
43
+ let loaded = false;
43
44
  // Validate file has .ts or .js extension
44
45
  if (!filePath.endsWith('.js') && !filePath.endsWith('.ts')) {
45
46
  throw new Error("File must be a .ts or .js");
@@ -49,9 +50,14 @@ export class CommandManager {
49
50
  console.error('[🆕🔴 ] Error loading command ' + chalk.blue(filePath.toString().replace(/^.*[\\\/]/, '').split('.').slice(0, -1).join('.')));
50
51
  console.log(e + '\n' + e.name + '\n' + e.stack);
51
52
  });
53
+ if (!command)
54
+ return;
52
55
  command = Object.values(command)[0];
53
56
  try {
54
57
  command = new command();
58
+ this.framework.commands.set(command.constructor.name.toLowerCase(), command);
59
+ console.debug('[🆕🟢 ] Command ' + chalk.blue(filePath.toString().replace(/^.*[\\\/]/, '').split('.').slice(0, -1).join('.')) + ' loaded');
60
+ loaded = true;
55
61
  }
56
62
  catch (error) {
57
63
  this.errorHandler.handleError(error, {
@@ -59,9 +65,8 @@ export class CommandManager {
59
65
  command: command,
60
66
  });
61
67
  }
62
- this.framework.commands.set(command.constructor.name.toLowerCase(), command);
63
- console.debug('[🆕🟢 ] Command ' + chalk.blue(filePath.toString().replace(/^.*[\\\/]/, '').split('.').slice(0, -1).join('.')) + ' loaded');
64
- return command;
68
+ if (loaded)
69
+ return command;
65
70
  }
66
71
  /**
67
72
  * Load all command files from a folder
@@ -77,12 +82,14 @@ export class CommandManager {
77
82
  continue;
78
83
  if (file.endsWith('.js') || file.endsWith('.ts')) {
79
84
  const command = await this.loadCommandFile(path.join(folderPath, file));
80
- const commandName = command.constructor.name.toLowerCase();
81
- if (options?.blacklist && options.blacklist.includes(commandName))
82
- continue;
83
- if (options?.whitelist && !options.whitelist.includes(commandName))
84
- continue;
85
- this.commands.set(options?.renames?.[commandName] || commandName, command);
85
+ if (command) {
86
+ const commandName = command.constructor.name.toLowerCase();
87
+ if (options?.blacklist && options.blacklist.includes(commandName))
88
+ continue;
89
+ if (options?.whitelist && !options.whitelist.includes(commandName))
90
+ continue;
91
+ this.commands.set(options?.renames?.[commandName] || commandName, command);
92
+ }
86
93
  }
87
94
  }
88
95
  return this.commands;
@@ -1,3 +1,5 @@
1
+ import { Guild } from "discord.js";
2
+ import { CommandArgDefinition } from "../definitions/commands/CommandArgDefinition";
1
3
  export declare class CommandParser {
2
4
  /**
3
5
  * From a command-line string, returns an array of parameters.
@@ -13,4 +15,9 @@ export declare class CommandParser {
13
15
  * splitCommandLine('a "b c"');
14
16
  */
15
17
  static splitCommandLine(commandLine: any): any;
18
+ static parseFromSplitedString(args: any, argDefinitions: CommandArgDefinition[], guild: Guild): Promise<{
19
+ validated: boolean;
20
+ errors: any[];
21
+ parsedArgs: Map<string, any>;
22
+ }>;
16
23
  }