@spatulox/simplediscordbot 1.0.1

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 (64) hide show
  1. package/.env.example +2 -0
  2. package/LICENSE.md +21 -0
  3. package/README.md +1 -0
  4. package/dist/bot/Bot.js +107 -0
  5. package/dist/bot/BotEnv.js +29 -0
  6. package/dist/bot/BotLog.js +90 -0
  7. package/dist/bot/BotMessage.js +79 -0
  8. package/dist/cli/BaseCLI.js +165 -0
  9. package/dist/cli/GenerationCLI/ContextMenuGeneratorCLI.js +109 -0
  10. package/dist/cli/GenerationCLI/GenerationCLI.js +25 -0
  11. package/dist/cli/GenerationCLI/InteractionGeneratorCLI.js +20 -0
  12. package/dist/cli/GenerationCLI/ModalGeneratorCLI.js +166 -0
  13. package/dist/cli/GenerationCLI/SlashCommandsGeneratorCLI.js +221 -0
  14. package/dist/cli/GenerationCLI.js +36 -0
  15. package/dist/cli/GuildListManager.js +61 -0
  16. package/dist/cli/InputCLI.js +25 -0
  17. package/dist/cli/InteractionCLI/InteractionCLI.js +30 -0
  18. package/dist/cli/InteractionCLI/InteractionCLIManager.js +80 -0
  19. package/dist/cli/InteractionCLI.js +109 -0
  20. package/dist/cli/MainCLI.js +32 -0
  21. package/dist/cli/type/ContextMenuConfig.js +2 -0
  22. package/dist/cli/type/InteractionType.js +14 -0
  23. package/dist/cli/type/SlashCommandConfig.js +2 -0
  24. package/dist/index.js +31 -0
  25. package/dist/manager/FileManager.js +136 -0
  26. package/dist/manager/direct/UserManager.js +76 -0
  27. package/dist/manager/discord/ChannelManager.js +48 -0
  28. package/dist/manager/discord/DiscordRegex.js +114 -0
  29. package/dist/manager/discord/GuildManager.js +67 -0
  30. package/dist/manager/discord/InviteManager.js +89 -0
  31. package/dist/manager/discord/RoleManager.js +83 -0
  32. package/dist/manager/discord/UserManager.js +69 -0
  33. package/dist/manager/guild/ChannelManager/ForumChannelManager.js +33 -0
  34. package/dist/manager/guild/ChannelManager/GuildChannelList.js +20 -0
  35. package/dist/manager/guild/ChannelManager/GuildChannelManager.js +91 -0
  36. package/dist/manager/guild/ChannelManager/GuildMessageManager.js +85 -0
  37. package/dist/manager/guild/ChannelManager/GuildTextChannelManager.js +33 -0
  38. package/dist/manager/guild/ChannelManager/GuildVoiceChannelManager.js +33 -0
  39. package/dist/manager/guild/ChannelManager/NewsChannelManager.js +33 -0
  40. package/dist/manager/guild/ChannelManager/StageChannelManager.js +33 -0
  41. package/dist/manager/guild/ChannelManager/ThreadChannelManager.js +34 -0
  42. package/dist/manager/guild/GuildManager.js +134 -0
  43. package/dist/manager/guild/GuildUserManager.js +212 -0
  44. package/dist/manager/guild/InviteManager.js +68 -0
  45. package/dist/manager/guild/InviteManager_old.js +89 -0
  46. package/dist/manager/guild/RoleManager.js +83 -0
  47. package/dist/manager/hadlers_old/builder/ModalManager.js +111 -0
  48. package/dist/manager/hadlers_old/builder/delete.js +49 -0
  49. package/dist/manager/hadlers_old/builder/deploy.js +225 -0
  50. package/dist/manager/hadlers_old/builder/interactions/CommandManager.js +14 -0
  51. package/dist/manager/hadlers_old/builder/interactions/ContextMenuManager.js +14 -0
  52. package/dist/manager/hadlers_old/builder/interactions/InteractionBase.js +341 -0
  53. package/dist/manager/hadlers_old/builder/interactions/InteractionManager.js +65 -0
  54. package/dist/manager/hadlers_old/builder/list.js +166 -0
  55. package/dist/manager/messages/EmbedManager.js +131 -0
  56. package/dist/manager/messages/ReactionManager.js +99 -0
  57. package/dist/manager/messages/WebhookManager.js +105 -0
  58. package/dist/type/FolderName.js +9 -0
  59. package/dist/utils/DiscordRegex.js +116 -0
  60. package/dist/utils/Log.js +28 -0
  61. package/dist/utils/SimpleMutex.js +39 -0
  62. package/dist/utils/network/InternetChecker.js +54 -0
  63. package/dist/utils/times/UnitTime.js +85 -0
  64. package/package.json +40 -0
@@ -0,0 +1,109 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.InteractionCLI = void 0;
4
+ const BaseCLI_1 = require("./BaseCLI");
5
+ const InteractionManager_1 = require("../manager/handlers/builder/interactions/InteractionManager");
6
+ const BotEnv_1 = require("../bot/BotEnv");
7
+ class InteractionCLI extends BaseCLI_1.BaseCLI {
8
+ constructor(parent) {
9
+ super(parent);
10
+ this.managers = {};
11
+ const { clientId, token } = BotEnv_1.BotEnv;
12
+ this.managers['CommandManager'] = new InteractionManager_1.CommandManager(clientId, token);
13
+ this.managers['ContextMenuManager'] = new InteractionManager_1.ContextMenuManager(clientId, token);
14
+ }
15
+ getTitle() {
16
+ return '🔄 Interaction Manager CLI';
17
+ }
18
+ async showMainMenu() {
19
+ console.clear();
20
+ console.log(this.getTitle());
21
+ console.log('═'.repeat(40));
22
+ console.log('1. CommandManager');
23
+ console.log('2. ContextMenuManager');
24
+ console.log('3. Back');
25
+ console.log('═'.repeat(40));
26
+ const choice = await this.prompt('Choose a manager: ');
27
+ switch (choice) {
28
+ case '1': return this.handleManager('CommandManager');
29
+ case '2': return this.handleManager('ContextMenuManager');
30
+ case '3': return this.goBack();
31
+ default: return this.showMainMenu();
32
+ }
33
+ }
34
+ async handleManager(key) {
35
+ const manager = this.managers[key];
36
+ if (!manager)
37
+ return;
38
+ console.clear();
39
+ console.log(`${key} - ${manager.folderPath}`);
40
+ console.log('═'.repeat(50));
41
+ console.log(`1. List remote ${manager.folderPath}`);
42
+ console.log(`2. Deploy local ${manager.folderPath}`);
43
+ console.log(`3. Update remote ${manager.folderPath}`);
44
+ console.log(`4. Delete remote ${manager.folderPath}`);
45
+ console.log('5. Back');
46
+ console.log('═'.repeat(50));
47
+ const choice = await this.prompt('Choose an action: ');
48
+ switch (choice) {
49
+ case '1':
50
+ await manager.list();
51
+ break;
52
+ case '2':
53
+ await this.handleDeploy(manager);
54
+ break;
55
+ case '3':
56
+ await this.handleUpdate(manager);
57
+ break;
58
+ case '4':
59
+ await this.handleDelete(manager);
60
+ break;
61
+ case '5':
62
+ case 'exit': return this.showMainMenu();
63
+ }
64
+ await this.prompt('Press Enter to continue...');
65
+ return this.handleManager(key);
66
+ }
67
+ async selectCommands(manager, remote = true) {
68
+ const handlerManagerType = `${manager.folderPath}(s)`;
69
+ const commandList = remote ? await manager.list() : await manager.listFromFile();
70
+ if (!commandList?.length) {
71
+ console.log(`No ${handlerManagerType} found`);
72
+ return [];
73
+ }
74
+ const input = await this.prompt('Enter numbers (ex: 1,3,5 or "all" or "exit"): ');
75
+ if (input.toLowerCase() === 'all') {
76
+ return commandList;
77
+ }
78
+ if (input.toLowerCase() === 'exit') {
79
+ return [];
80
+ }
81
+ const indices = input.split(',').map(i => parseInt(i.trim())).filter(i => !isNaN(i));
82
+ const selected = commandList.filter((cmd) => indices.includes(cmd.index));
83
+ if (selected.length === 0) {
84
+ console.log('Invalid number');
85
+ return [];
86
+ }
87
+ console.log(`${selected.length} selected ${handlerManagerType}`);
88
+ return selected;
89
+ }
90
+ async handleDeploy(manager) {
91
+ const selected = await this.selectCommands(manager, false);
92
+ if (selected.length === 0)
93
+ return;
94
+ await manager.deploy(selected);
95
+ }
96
+ async handleUpdate(manager) {
97
+ const selected = await this.selectCommands(manager);
98
+ if (selected.length === 0)
99
+ return;
100
+ await manager.update(selected);
101
+ }
102
+ async handleDelete(manager) {
103
+ const selected = await this.selectCommands(manager);
104
+ if (selected.length === 0)
105
+ return;
106
+ await manager.delete(selected);
107
+ }
108
+ }
109
+ exports.InteractionCLI = InteractionCLI;
@@ -0,0 +1,32 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.MainCLI = void 0;
5
+ const BaseCLI_1 = require("./BaseCLI");
6
+ const InteractionCLI_1 = require("./InteractionCLI/InteractionCLI");
7
+ const GenerationCLI_1 = require("./GenerationCLI/GenerationCLI");
8
+ /**
9
+ * --- MainCLI ---
10
+ * Main controller for sub menu
11
+ */
12
+ class MainCLI extends BaseCLI_1.BaseCLI {
13
+ getTitle() {
14
+ return "💠 SimpleDiscordBot CLI";
15
+ }
16
+ constructor() {
17
+ super();
18
+ this.menuSelection = [
19
+ { label: "Manage Interactions", action: () => new InteractionCLI_1.InteractionCLI(this) },
20
+ { label: "Generate Files", action: () => new GenerationCLI_1.GenerationCLI(this) },
21
+ { label: "Help", action: () => this.showHelp() },
22
+ { label: "Exit", action: () => this },
23
+ ];
24
+ this.showMainMenu();
25
+ }
26
+ execute() {
27
+ console.log("👋 Bye !");
28
+ process.exit();
29
+ }
30
+ }
31
+ exports.MainCLI = MainCLI;
32
+ new MainCLI();
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.InteractionContextType = exports.InteractionIntegrationType = void 0;
4
+ var InteractionIntegrationType;
5
+ (function (InteractionIntegrationType) {
6
+ InteractionIntegrationType[InteractionIntegrationType["GUILD_INSTALL"] = 0] = "GUILD_INSTALL";
7
+ InteractionIntegrationType[InteractionIntegrationType["USER_INSTALL"] = 1] = "USER_INSTALL";
8
+ })(InteractionIntegrationType || (exports.InteractionIntegrationType = InteractionIntegrationType = {}));
9
+ var InteractionContextType;
10
+ (function (InteractionContextType) {
11
+ InteractionContextType[InteractionContextType["SERVER_CHANNEL"] = 0] = "SERVER_CHANNEL";
12
+ InteractionContextType[InteractionContextType["BOT_DM"] = 1] = "BOT_DM";
13
+ InteractionContextType[InteractionContextType["GROUP_DM"] = 2] = "GROUP_DM";
14
+ })(InteractionContextType || (exports.InteractionContextType = InteractionContextType = {}));
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
package/dist/index.js ADDED
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.DiscordRegex = exports.SimpleMutex = exports.Log = exports.Time = exports.ModalManager = exports.UserManager = exports.GuildManager = exports.ReactionManager = exports.WebhookManager = exports.EmbedColor = exports.EmbedManager = exports.FileManager = exports.Bot = void 0;
4
+ var Bot_1 = require("./bot/Bot");
5
+ Object.defineProperty(exports, "Bot", { enumerable: true, get: function () { return Bot_1.Bot; } });
6
+ // Manager
7
+ var FileManager_1 = require("./manager/FileManager");
8
+ Object.defineProperty(exports, "FileManager", { enumerable: true, get: function () { return FileManager_1.FileManager; } });
9
+ var EmbedManager_1 = require("./manager/messages/EmbedManager");
10
+ Object.defineProperty(exports, "EmbedManager", { enumerable: true, get: function () { return EmbedManager_1.EmbedManager; } });
11
+ Object.defineProperty(exports, "EmbedColor", { enumerable: true, get: function () { return EmbedManager_1.EmbedColor; } });
12
+ var WebhookManager_1 = require("./manager/messages/WebhookManager");
13
+ Object.defineProperty(exports, "WebhookManager", { enumerable: true, get: function () { return WebhookManager_1.WebhookManager; } });
14
+ var ReactionManager_1 = require("./manager/messages/ReactionManager");
15
+ Object.defineProperty(exports, "ReactionManager", { enumerable: true, get: function () { return ReactionManager_1.ReactionManager; } });
16
+ var GuildManager_1 = require("./manager/guild/GuildManager");
17
+ Object.defineProperty(exports, "GuildManager", { enumerable: true, get: function () { return GuildManager_1.GuildManager; } });
18
+ var UserManager_1 = require("./manager/direct/UserManager");
19
+ Object.defineProperty(exports, "UserManager", { enumerable: true, get: function () { return UserManager_1.UserManager; } });
20
+ // Handlers
21
+ var ModalManager_1 = require("./manager/handlers/builder/ModalManager");
22
+ Object.defineProperty(exports, "ModalManager", { enumerable: true, get: function () { return ModalManager_1.ModalManager; } });
23
+ // Utils
24
+ var UnitTime_1 = require("./utils/times/UnitTime");
25
+ Object.defineProperty(exports, "Time", { enumerable: true, get: function () { return UnitTime_1.Time; } });
26
+ var Log_1 = require("./utils/Log");
27
+ Object.defineProperty(exports, "Log", { enumerable: true, get: function () { return Log_1.Log; } });
28
+ var SimpleMutex_1 = require("./utils/SimpleMutex");
29
+ Object.defineProperty(exports, "SimpleMutex", { enumerable: true, get: function () { return SimpleMutex_1.SimpleMutex; } });
30
+ var DiscordRegex_1 = require("./utils/DiscordRegex");
31
+ Object.defineProperty(exports, "DiscordRegex", { enumerable: true, get: function () { return DiscordRegex_1.DiscordRegex; } });
@@ -0,0 +1,136 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.FileManager = void 0;
7
+ // src/filesystem/FileManager.ts
8
+ const path_1 = __importDefault(require("path"));
9
+ const promises_1 = __importDefault(require("fs/promises"));
10
+ const Log_1 = require("../utils/Log");
11
+ const Bot_1 = require("../bot/Bot");
12
+ const EmbedManager_1 = require("./messages/EmbedManager");
13
+ class FileManager {
14
+ /**
15
+ * Reads a JSON file synchronously.
16
+ * @param filePath Full path to the JSON file
17
+ * @returns Parsed JSON object or 'Error' string on failure
18
+ */
19
+ static async readJsonFile(filePath) {
20
+ try {
21
+ const data = await promises_1.default.readFile(filePath, 'utf8');
22
+ return JSON.parse(data);
23
+ }
24
+ catch (error) {
25
+ Log_1.Log.error(`Failed to read JSON file ${filePath}: ${error}`);
26
+ return false;
27
+ }
28
+ }
29
+ /**
30
+ * Lists all directories in a given path.
31
+ * @param directoryPath Path to scan for directories
32
+ * @returns Array of directory names or false on error
33
+ */
34
+ static async listDirectories(directoryPath) {
35
+ try {
36
+ const files = await promises_1.default.readdir(directoryPath, { withFileTypes: true });
37
+ const directories = files
38
+ .filter(file => file.isDirectory())
39
+ .map(dir => dir.name);
40
+ return directories;
41
+ }
42
+ catch (error) {
43
+ Log_1.Log.error(`Failed to read directory ${directoryPath}: ${error}`);
44
+ return false;
45
+ }
46
+ }
47
+ /**
48
+ * Lists all JSON files in a directory.
49
+ * @param directoryPath Path to scan for JSON files
50
+ * @returns Array of JSON filenames or false on error
51
+ */
52
+ static async listJsonFiles(directoryPath) {
53
+ try {
54
+ const files = await promises_1.default.readdir(directoryPath);
55
+ return files.filter(file => path_1.default.extname(file) === '.json');
56
+ }
57
+ catch (error) {
58
+ Log_1.Log.error(`Failed to read directory ${directoryPath}: ${error}`);
59
+ return false;
60
+ }
61
+ }
62
+ /**
63
+ * Lists files with specific extension in a directory.
64
+ * @param directoryPath Path to scan
65
+ * @param extension File extension (with or without dot)
66
+ * @returns Array of matching filenames or 'Error' string on failure
67
+ */
68
+ static async listFiles(directoryPath, extension) {
69
+ if (typeof directoryPath !== 'string' || typeof extension !== 'string') {
70
+ Log_1.Log.error('Directory path and extension must be strings');
71
+ return false;
72
+ }
73
+ try {
74
+ let ext = extension;
75
+ if (ext.startsWith('.')) {
76
+ ext = ext.slice(1);
77
+ }
78
+ const files = await promises_1.default.readdir(directoryPath);
79
+ return files.filter(file => path_1.default.extname(file) === `.${ext}`);
80
+ }
81
+ catch (error) {
82
+ Log_1.Log.error(`Failed to read directory ${directoryPath}: ${error}`);
83
+ return false;
84
+ }
85
+ }
86
+ /**
87
+ * Creates directory structure and writes JSON data to file.
88
+ * @param directoryPath Full directory path (creates if missing)
89
+ * @param filename Filename without extension
90
+ * @param data Data to write (JSON serializable)
91
+ * @param sendErrorToErrorChannel Send error to the error channel
92
+ * @returns true on success, false on failure
93
+ */
94
+ static async writeJsonFile(directoryPath, filename, data, sendErrorToErrorChannel = true) {
95
+ // Skip if data is an Error array
96
+ if (Array.isArray(data) && data.length === 1 && data[0] === 'Error') {
97
+ Log_1.Log.error(`Cannot save data for ${filename}: data contains 'Error'`);
98
+ return false;
99
+ }
100
+ try {
101
+ // Create directory structure recursively
102
+ const directories = directoryPath.split(path_1.default.sep).filter(Boolean);
103
+ let currentPath = '';
104
+ for (const dir of directories) {
105
+ currentPath = path_1.default.join(currentPath, dir);
106
+ try {
107
+ await promises_1.default.access(currentPath);
108
+ }
109
+ catch {
110
+ await promises_1.default.mkdir(currentPath, { recursive: true });
111
+ }
112
+ }
113
+ if (!filename || filename.trim() === '') {
114
+ Log_1.Log.error('Cannot write JSON file: empty filename');
115
+ return false;
116
+ }
117
+ const cleanFilename = filename.replace(/\.json$/i, '');
118
+ const filePath = path_1.default.join(directoryPath, `${cleanFilename}.json`);
119
+ const jsonContent = JSON.stringify(data, null, 2);
120
+ await promises_1.default.writeFile(filePath, jsonContent);
121
+ Log_1.Log.info(`Successfully wrote data to ${filePath}`);
122
+ return true;
123
+ }
124
+ catch (error) {
125
+ const cleanFilename = filename.replace(/\.json$/i, '') || 'unknown';
126
+ if (sendErrorToErrorChannel) {
127
+ await Bot_1.Bot.log.sendError(EmbedManager_1.EmbedManager.error(`Failed to write file ${directoryPath}/${cleanFilename}.json: ${error}`));
128
+ }
129
+ else {
130
+ Log_1.Log.error(`Failed to write file ${directoryPath}/${cleanFilename}.json: ${error}`);
131
+ }
132
+ return false;
133
+ }
134
+ }
135
+ }
136
+ exports.FileManager = FileManager;
@@ -0,0 +1,76 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.UserManager = void 0;
4
+ const Bot_1 = require("../../bot/Bot");
5
+ const Log_1 = require("../../utils/Log");
6
+ class UserManager {
7
+ /**
8
+ * Find a member
9
+ */
10
+ static async find(userId) {
11
+ try {
12
+ return await Bot_1.Bot.client.users.fetch(userId);
13
+ }
14
+ catch (error) {
15
+ Log_1.Log.error(`UserManager: Member ${userId} not found`);
16
+ return null;
17
+ }
18
+ }
19
+ /**
20
+ * Find member in specific guild
21
+ */
22
+ static async findInGuild(guildId, memberId) {
23
+ try {
24
+ const guild = Bot_1.Bot.client.guilds.cache.get(guildId);
25
+ if (!guild)
26
+ throw new Error(`Guild ${guildId} not found`);
27
+ const member = await guild.members.fetch({ user: memberId, force: true });
28
+ return member ?? null;
29
+ }
30
+ catch (error) {
31
+ Log_1.Log.error(`UserManager: Member ${memberId} not found in ${guildId}`);
32
+ return null;
33
+ }
34
+ }
35
+ /**
36
+ * Check if user is still in guild
37
+ */
38
+ static async isInGuild(guildId, userId) {
39
+ try {
40
+ const guild = Bot_1.Bot.client.guilds.cache.get(guildId);
41
+ if (!guild)
42
+ return false;
43
+ await guild.members.fetch({ user: userId, force: true });
44
+ return true;
45
+ }
46
+ catch (error) {
47
+ return error.code !== 10007; // Unknown Member
48
+ }
49
+ }
50
+ /**
51
+ * Impl
52
+ */
53
+ static async send(user_id_or_user, content_or_options) {
54
+ try {
55
+ let user;
56
+ if (typeof user_id_or_user === 'string') {
57
+ user = await Bot_1.Bot.client.users.fetch(user_id_or_user);
58
+ }
59
+ else {
60
+ user = user_id_or_user;
61
+ }
62
+ const dmChannel = await user.createDM();
63
+ const payload = typeof content_or_options === 'string'
64
+ ? { content: content_or_options }
65
+ : content_or_options;
66
+ const message = await dmChannel.send(payload);
67
+ Log_1.Log.info(`Sent DM to ${user.id} (${user.username}): "${(payload.content || 'Embed').substring(0, 50)}..."`);
68
+ return message;
69
+ }
70
+ catch (error) {
71
+ Log_1.Log.error(`Failed to send DM to ${user_id_or_user}: ${error}`);
72
+ throw new Error(`Cannot send DM to ${user_id_or_user}`);
73
+ }
74
+ }
75
+ }
76
+ exports.UserManager = UserManager;
@@ -0,0 +1,48 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ChannelManager = void 0;
4
+ const Bot_1 = require("../../bot/Bot");
5
+ const Log_1 = require("../../utils/Log");
6
+ class ChannelManager {
7
+ /**
8
+ * Search text-based channel by ID (cache or fetch)
9
+ */
10
+ static async find(channelId) {
11
+ try {
12
+ const channel = Bot_1.Bot.client.channels.cache.get(channelId) || await Bot_1.Bot.client.channels.fetch(channelId);
13
+ return channel?.isTextBased() ? channel : null;
14
+ }
15
+ catch (error) {
16
+ Log_1.Log.error(`ChannelManager: Failed to fetch ${channelId}: ${error}`);
17
+ return null;
18
+ }
19
+ }
20
+ /**
21
+ * Find channel in specific guild
22
+ */
23
+ static async findInGuild(guildId, channelId) {
24
+ try {
25
+ const guild = Bot_1.Bot.client.guilds.cache.get(guildId);
26
+ if (!guild)
27
+ return null;
28
+ const channel = guild.channels.cache.get(channelId);
29
+ return channel?.isTextBased() ? channel : null;
30
+ }
31
+ catch (error) {
32
+ Log_1.Log.error(`ChannelManager: Failed guild channel ${guildId}/${channelId}: ${error}`);
33
+ return null;
34
+ }
35
+ }
36
+ /**
37
+ * Get all text channels in guild
38
+ */
39
+ static getTextChannelsInGuild(guildId) {
40
+ const guild = Bot_1.Bot.client.guilds.cache.get(guildId);
41
+ if (!guild)
42
+ return [];
43
+ return guild.channels.cache
44
+ .filter(channel => channel.isTextBased() && channel.type !== 11) // Exclude threads
45
+ .map(channel => channel);
46
+ }
47
+ }
48
+ exports.ChannelManager = ChannelManager;
@@ -0,0 +1,114 @@
1
+ "use strict";
2
+ var _a;
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.DiscordRegex = void 0;
5
+ /**
6
+ * Classe utilitaire pour valider tous les formats Discord avec regex
7
+ */
8
+ class DiscordRegex {
9
+ /**
10
+ * Validate Discord ID Discord (18)
11
+ */
12
+ static isDiscordId(id) {
13
+ return this.DISCORD_ID.test(id);
14
+ }
15
+ /**
16
+ * Validate a bot ID (19)
17
+ */
18
+ static isBotMention(mention) {
19
+ return this.BOT_REGEX.test(mention);
20
+ }
21
+ /**
22
+ * Validate a User ping
23
+ */
24
+ static isUserMention(mention) {
25
+ return this.USER_REGEX.test(mention);
26
+ }
27
+ /**
28
+ * Validate a Discord username
29
+ */
30
+ static isUsername(username) {
31
+ return this.USERNAME.test(username);
32
+ }
33
+ /**
34
+ * Type guard for Discord ID
35
+ */
36
+ static isDiscordIdType(id) {
37
+ return this.isDiscordId(id);
38
+ }
39
+ /**
40
+ * Any Discord URL
41
+ */
42
+ static isDiscordUrl(url) {
43
+ return this.URL_REGEX.test(url) || this.INVITE.test(url);
44
+ }
45
+ /**
46
+ * Any discord mention
47
+ */
48
+ static isAnyMention(text) {
49
+ return this.DISCORD_MENTION_REGEX.test(text);
50
+ }
51
+ /**
52
+ * List all regex
53
+ */
54
+ static listAll() {
55
+ return {
56
+ SPACE: this.SPACE,
57
+ URL_REGEX: this.URL_REGEX,
58
+ USER_REGEX: this.USER_REGEX,
59
+ BOT_REGEX: this.BOT_REGEX,
60
+ CHANNEL_REGEX: this.CHANNEL_REGEX,
61
+ ROLE_REGEX: this.ROLE_REGEX,
62
+ DISCORD_PING_REGEX: this.DISCORD_PING_REGEX,
63
+ DISCORD_MENTION_REGEX: this.DISCORD_MENTION_REGEX,
64
+ DISCORD_ID: this.DISCORD_ID,
65
+ USERNAME: this.USERNAME,
66
+ USERNAME_DISCRIM: this.USERNAME_DISCRIM,
67
+ CHANNEL_MENTION: this.CHANNEL_MENTION,
68
+ USER_MENTION: this.USER_MENTION,
69
+ ROLE_MENTION: this.ROLE_MENTION,
70
+ INVITE: this.INVITE,
71
+ EMOJI: this.EMOJI
72
+ };
73
+ }
74
+ }
75
+ exports.DiscordRegex = DiscordRegex;
76
+ _a = DiscordRegex;
77
+ // Caractères spéciaux
78
+ DiscordRegex.SPACE = "\u200B";
79
+ // URLs basiques
80
+ DiscordRegex.URL_REGEX = /(https?:\/\/[^s]+)/;
81
+ /* DISCORD REGEX */
82
+ DiscordRegex.USER_REGEX = /<@\d{18}>/;
83
+ DiscordRegex.BOT_REGEX = /<@\d{19}>/;
84
+ DiscordRegex.CHANNEL_REGEX = /(<#\d{19}>)|(<id:(browse|customize|guide)>)/;
85
+ DiscordRegex.ROLE_REGEX = /<@&\d{19}>/;
86
+ /**
87
+ * Mention a User
88
+ * Mention a Role
89
+ */
90
+ DiscordRegex.DISCORD_PING_REGEX = new RegExp(`(${_a.USER_REGEX.source})|(${_a.BOT_REGEX.source})|(${_a.ROLE_REGEX.source})`);
91
+ /**
92
+ * Mention a User
93
+ * Mention a Role
94
+ * Mention a Channel
95
+ */
96
+ DiscordRegex.DISCORD_MENTION_REGEX = new RegExp(`(${_a.DISCORD_PING_REGEX.source})|(${_a.CHANNEL_REGEX.source})`);
97
+ // ID Discord (18 chiffres exactement)
98
+ DiscordRegex.DISCORD_ID = /^[0-9]{18}$/;
99
+ // ID utilisateur/guild/channel (18 chiffres)
100
+ DiscordRegex.SNOWFLAKE = /^[0-9]{18}$/;
101
+ // Username Discord (2-32 caractères alphanumériques + _ .)
102
+ DiscordRegex.USERNAME = /^[a-zA-Z0-9_]{2,32}$/;
103
+ // Username + discrim (ancien format)
104
+ DiscordRegex.USERNAME_DISCRIM = /^[a-zA-Z0-9_]{2,32}#\d{4}$/;
105
+ // Channel mention <#123456789012345678>
106
+ DiscordRegex.CHANNEL_MENTION = /^<#([0-9]{18})>$/;
107
+ // User mention <@123456789012345678> ou <@!123456789012345678>
108
+ DiscordRegex.USER_MENTION = /^<@!?([0-9]{18})>$/;
109
+ // Role mention <@&123456789012345678>
110
+ DiscordRegex.ROLE_MENTION = /^<@&([0-9]{18})>$/;
111
+ // URL Invite Discord
112
+ DiscordRegex.INVITE = /^discord(?:app\.com\/invite|gg)\/[a-zA-Z0-9]+$/;
113
+ // Emoji Discord (custom or unicode)
114
+ DiscordRegex.EMOJI = /^<a?:[a-zA-Z0-9_]{2,32}:[0-9]{18}>$|^[\u{1F300}-\u{1F5FF}\u{1F600}-\u{1F64F}\u{1F680}-\u{1F6FF}\u{2600}-\u{26FF}\u{2700}-\u{27BF}]+$/u;
@@ -0,0 +1,67 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.GuildManager = void 0;
4
+ const Log_1 = require("../../utils/Log");
5
+ const UnitTime_1 = require("../../utils/times/UnitTime");
6
+ const ChannelManager_1 = require("./ChannelManager");
7
+ const UserManager_1 = require("./UserManager");
8
+ class GuildManager {
9
+ /**
10
+ * Search channel by ID (TextChannel, DMChannel, ThreadChannel)
11
+ */
12
+ static async searchChannel(guildId, channelId) {
13
+ try {
14
+ return await ChannelManager_1.ChannelManager.findInGuild(guildId, channelId);
15
+ }
16
+ catch (error) {
17
+ Log_1.Log.error(`Failed to fetch channel ${channelId}: ${error}`);
18
+ return null;
19
+ }
20
+ }
21
+ /**
22
+ * Search guild member by ID
23
+ */
24
+ static async searchMember(memberId, guildId) {
25
+ try {
26
+ return await UserManager_1.UserManager.findInGuild(guildId, guildId);
27
+ }
28
+ catch (error) {
29
+ Log_1.Log.error(`Failed to fetch member ${memberId} in guild ${guildId}: ${error}`);
30
+ return null;
31
+ }
32
+ }
33
+ /**
34
+ * Check if member is still in guild
35
+ */
36
+ static async isMemberInGuild(memberId, guildId) {
37
+ try {
38
+ return await UserManager_1.UserManager.isInGuild(memberId, guildId);
39
+ }
40
+ catch (error) {
41
+ return error.code !== 10007; // Unknown Member
42
+ }
43
+ }
44
+ /**
45
+ * Fetch all members with retry logic
46
+ */
47
+ static async fetchAllMembers(guild) {
48
+ const MAX_ATTEMPTS = 3;
49
+ const RETRY_DELAY = UnitTime_1.Time.minute.MIN_05.toMilliseconds();
50
+ for (let attempt = 1; attempt <= MAX_ATTEMPTS; attempt++) {
51
+ try {
52
+ Log_1.Log.info(`Fetching members for ${guild.name} (attempt ${attempt})`);
53
+ const members = await guild.members.fetch();
54
+ Log_1.Log.info(`${guild.name}: ${members.size} members fetched`);
55
+ return members;
56
+ }
57
+ catch (error) {
58
+ Log_1.Log.error(`Guild ${guild.name} fetch failed (attempt ${attempt}): ${error}`);
59
+ if (attempt < MAX_ATTEMPTS) {
60
+ await new Promise(r => setTimeout(r, RETRY_DELAY));
61
+ }
62
+ }
63
+ }
64
+ throw new Error(`Failed to fetch members for ${guild.id} after ${MAX_ATTEMPTS} attempts`);
65
+ }
66
+ }
67
+ exports.GuildManager = GuildManager;