@spatulox/simplediscordbot 1.7.1 → 2.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.
- package/CHANGELOG.md +10 -0
- package/README.md +4 -6
- package/dist/index.d.mts +32 -32
- package/dist/index.d.ts +32 -32
- package/dist/index.js +214 -148
- package/dist/index.mjs +146 -84
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -5248,7 +5248,7 @@ var InternetChecker = class {
|
|
|
5248
5248
|
tries > 0 ? `Ping failed (${errorMsg}) - Attempt ${attempt}/${tries}` : `Ping failed (${errorMsg}) - Retrying in ${this.RETRY_TIME.toSeconds()} seconds...`
|
|
5249
5249
|
);
|
|
5250
5250
|
try {
|
|
5251
|
-
await new Promise((
|
|
5251
|
+
await new Promise((resolve2) => setTimeout(resolve2, this.RETRY_TIME.toMilliseconds()));
|
|
5252
5252
|
} catch {
|
|
5253
5253
|
Log.error("Retry delay failed.");
|
|
5254
5254
|
}
|
|
@@ -5418,31 +5418,85 @@ var _BotLog = class _BotLog {
|
|
|
5418
5418
|
Log.warn("Client not ready for Discord logging init");
|
|
5419
5419
|
return;
|
|
5420
5420
|
}
|
|
5421
|
-
|
|
5422
|
-
|
|
5423
|
-
|
|
5424
|
-
|
|
5425
|
-
|
|
5426
|
-
|
|
5427
|
-
|
|
5428
|
-
|
|
5429
|
-
|
|
5430
|
-
Log.error(`Log channel fetch failed: ${error}`);
|
|
5431
|
-
}
|
|
5432
|
-
}
|
|
5433
|
-
if (Bot.config.log?.errorChannelId) {
|
|
5421
|
+
const logTypes = [
|
|
5422
|
+
{ config: "info", prop: "logChannel" },
|
|
5423
|
+
{ config: "warn", prop: "warnChannel" },
|
|
5424
|
+
{ config: "error", prop: "errorChannel" },
|
|
5425
|
+
{ config: "debug", prop: "debugChannel" }
|
|
5426
|
+
];
|
|
5427
|
+
for (const { config, prop } of logTypes) {
|
|
5428
|
+
const channelId = Bot.config.log?.[config]?.channelId;
|
|
5429
|
+
if (!channelId) continue;
|
|
5434
5430
|
try {
|
|
5435
|
-
const
|
|
5436
|
-
if (
|
|
5437
|
-
_BotLog
|
|
5431
|
+
const channel = await Bot.client.channels.fetch(channelId);
|
|
5432
|
+
if (channel?.isTextBased()) {
|
|
5433
|
+
_BotLog[prop] = channel;
|
|
5438
5434
|
} else {
|
|
5439
|
-
Log.warn(
|
|
5435
|
+
Log.warn(`${config.charAt(0).toUpperCase() + config.slice(1)} channel ${channelId} invalid`);
|
|
5440
5436
|
}
|
|
5441
5437
|
} catch (error) {
|
|
5442
|
-
Log.error(
|
|
5438
|
+
Log.error(`${config.charAt(0).toUpperCase() + config.slice(1)} channel fetch failed: ${error}`);
|
|
5443
5439
|
}
|
|
5444
5440
|
}
|
|
5445
5441
|
}
|
|
5442
|
+
/*public static async initDiscordLogging(): Promise<void> {
|
|
5443
|
+
if (!Bot.client.isReady()) {
|
|
5444
|
+
Log.warn('Client not ready for Discord logging init');
|
|
5445
|
+
return;
|
|
5446
|
+
}
|
|
5447
|
+
|
|
5448
|
+
if (Bot.config.log?.info.channelId) {
|
|
5449
|
+
try {
|
|
5450
|
+
const logCh = await Bot.client.channels.fetch(Bot.config.log.info.channelId) as TextChannel;
|
|
5451
|
+
if (logCh?.isTextBased()) {
|
|
5452
|
+
BotLog.logChannel = logCh;
|
|
5453
|
+
} else {
|
|
5454
|
+
Log.warn(`Log channel ${Bot.config.log.info.channelId} invalid`);
|
|
5455
|
+
}
|
|
5456
|
+
} catch (error) {
|
|
5457
|
+
Log.error(`Log channel fetch failed: ${error}`);
|
|
5458
|
+
}
|
|
5459
|
+
}
|
|
5460
|
+
|
|
5461
|
+
if (Bot.config.log?.warn.channelId) {
|
|
5462
|
+
try {
|
|
5463
|
+
const errorCh = await Bot.client.channels.fetch(Bot.config.log.warn.channelId) as TextChannel;
|
|
5464
|
+
if (errorCh?.isTextBased()) {
|
|
5465
|
+
BotLog.warnChannel = errorCh;
|
|
5466
|
+
} else {
|
|
5467
|
+
Log.warn(`Warn channel ${Bot.config.log.warn.channelId} invalid`);
|
|
5468
|
+
}
|
|
5469
|
+
} catch (error) {
|
|
5470
|
+
Log.error(`Warn channel fetch failed: ${error}`);
|
|
5471
|
+
}
|
|
5472
|
+
}
|
|
5473
|
+
|
|
5474
|
+
if (Bot.config.log?.error.channelId) {
|
|
5475
|
+
try {
|
|
5476
|
+
const errorCh = await Bot.client.channels.fetch(Bot.config.log.error.channelId) as TextChannel;
|
|
5477
|
+
if (errorCh?.isTextBased()) {
|
|
5478
|
+
BotLog.errorChannel = errorCh;
|
|
5479
|
+
} else {
|
|
5480
|
+
Log.warn(`Error channel ${Bot.config.log.error.channelId} invalid`);
|
|
5481
|
+
}
|
|
5482
|
+
} catch (error) {
|
|
5483
|
+
Log.error(`Error channel fetch failed: ${error}`);
|
|
5484
|
+
}
|
|
5485
|
+
}
|
|
5486
|
+
|
|
5487
|
+
if (Bot.config.log?.debug.channelId) {
|
|
5488
|
+
try {
|
|
5489
|
+
const errorCh = await Bot.client.channels.fetch(Bot.config.log.debug.channelId) as TextChannel;
|
|
5490
|
+
if (errorCh?.isTextBased()) {
|
|
5491
|
+
BotLog.debugChannel = errorCh;
|
|
5492
|
+
} else {
|
|
5493
|
+
Log.warn(`Debug channel ${Bot.config.log.debug.channelId} invalid`);
|
|
5494
|
+
}
|
|
5495
|
+
} catch (error) {
|
|
5496
|
+
Log.error(`Debug channel fetch failed: ${error}`);
|
|
5497
|
+
}
|
|
5498
|
+
}
|
|
5499
|
+
}*/
|
|
5446
5500
|
/**
|
|
5447
5501
|
* Send content to specific Discord channel
|
|
5448
5502
|
*/
|
|
@@ -5509,8 +5563,8 @@ var _BotLog = class _BotLog {
|
|
|
5509
5563
|
Log.warn(content);
|
|
5510
5564
|
}
|
|
5511
5565
|
}
|
|
5512
|
-
if (logConfig?.warn.discord && this.
|
|
5513
|
-
return await this._sendToChannel(this.
|
|
5566
|
+
if (logConfig?.warn.discord && this.warnChannel) {
|
|
5567
|
+
return await this._sendToChannel(this.warnChannel, content, "warn");
|
|
5514
5568
|
}
|
|
5515
5569
|
}
|
|
5516
5570
|
/**
|
|
@@ -5523,12 +5577,14 @@ var _BotLog = class _BotLog {
|
|
|
5523
5577
|
Log.debug(content);
|
|
5524
5578
|
}
|
|
5525
5579
|
}
|
|
5526
|
-
if (logConfig?.debug.discord && this.
|
|
5527
|
-
return await this._sendToChannel(this.
|
|
5580
|
+
if (logConfig?.debug.discord && this.debugChannel) {
|
|
5581
|
+
return await this._sendToChannel(this.debugChannel, content, "debug");
|
|
5528
5582
|
}
|
|
5529
5583
|
}
|
|
5530
5584
|
};
|
|
5531
5585
|
_BotLog.logChannel = null;
|
|
5586
|
+
_BotLog.warnChannel = null;
|
|
5587
|
+
_BotLog.debugChannel = null;
|
|
5532
5588
|
_BotLog.errorChannel = null;
|
|
5533
5589
|
var BotLog = _BotLog;
|
|
5534
5590
|
|
|
@@ -5647,8 +5703,8 @@ var EmbedManager = class {
|
|
|
5647
5703
|
/**
|
|
5648
5704
|
* Quick field adder
|
|
5649
5705
|
*/
|
|
5650
|
-
static field(embed,
|
|
5651
|
-
return embed.addFields({ name, value, inline });
|
|
5706
|
+
static field(embed, field) {
|
|
5707
|
+
return embed.addFields({ name: field.name, value: field.value, inline: field.inline ?? false });
|
|
5652
5708
|
}
|
|
5653
5709
|
static fields(embed, fields) {
|
|
5654
5710
|
fields.forEach((f3) => {
|
|
@@ -14309,7 +14365,7 @@ var _Bot = class _Bot {
|
|
|
14309
14365
|
Log.error(`Connection error : ${error}. Trying again...`);
|
|
14310
14366
|
tries++;
|
|
14311
14367
|
await new Promise(
|
|
14312
|
-
(
|
|
14368
|
+
(resolve2) => setTimeout(resolve2, Time.second.SEC_03.toMilliseconds())
|
|
14313
14369
|
);
|
|
14314
14370
|
}
|
|
14315
14371
|
}
|
|
@@ -14472,88 +14528,104 @@ var FileManager = class {
|
|
|
14472
14528
|
|
|
14473
14529
|
// src/manager/messages/WebhookManager.ts
|
|
14474
14530
|
import {
|
|
14475
|
-
|
|
14531
|
+
TextChannel as TextChannel3
|
|
14476
14532
|
} from "discord.js";
|
|
14533
|
+
import { readFile } from "fs/promises";
|
|
14534
|
+
import { resolve } from "path";
|
|
14477
14535
|
var WebhookManager = class {
|
|
14478
|
-
constructor(
|
|
14479
|
-
this.
|
|
14536
|
+
constructor(client, name, avatarPathOrUrl) {
|
|
14537
|
+
this.client = client;
|
|
14480
14538
|
this.name = name;
|
|
14481
|
-
this.
|
|
14539
|
+
this.avatarPathOrUrl = avatarPathOrUrl;
|
|
14482
14540
|
this.webhook = null;
|
|
14483
14541
|
}
|
|
14484
|
-
|
|
14485
|
-
|
|
14542
|
+
async getAvatar() {
|
|
14543
|
+
if (!this.avatarPathOrUrl) return null;
|
|
14544
|
+
if (this.avatarPathOrUrl.startsWith("http://") || this.avatarPathOrUrl.startsWith("https://")) {
|
|
14545
|
+
return this.avatarPathOrUrl;
|
|
14546
|
+
}
|
|
14547
|
+
try {
|
|
14548
|
+
const resolvedPath = resolve(process.cwd(), this.avatarPathOrUrl);
|
|
14549
|
+
return await readFile(resolvedPath);
|
|
14550
|
+
} catch (error) {
|
|
14551
|
+
Bot.log.warn(`Failed to load avatar from ${this.avatarPathOrUrl}: ${error}`);
|
|
14552
|
+
return null;
|
|
14553
|
+
}
|
|
14554
|
+
}
|
|
14555
|
+
/**
|
|
14556
|
+
* Récupère le channel à partir de l'ID ou utilise directement si TextChannel/ThreadChannel
|
|
14557
|
+
*/
|
|
14558
|
+
async getTextChannel(channelId) {
|
|
14559
|
+
const channel = await this.client.channels.fetch(channelId);
|
|
14560
|
+
if (!channel || !(channel instanceof TextChannel3)) {
|
|
14561
|
+
throw new Error(`Channel ${channelId} is not a TextChannel`);
|
|
14562
|
+
}
|
|
14563
|
+
return channel;
|
|
14486
14564
|
}
|
|
14487
14565
|
/**
|
|
14488
14566
|
* Get or create webhook (lazy initialization)
|
|
14489
14567
|
*/
|
|
14490
|
-
async getWebhook() {
|
|
14568
|
+
async getWebhook(channelId) {
|
|
14491
14569
|
if (this.webhook) return this.webhook;
|
|
14492
14570
|
try {
|
|
14493
|
-
const
|
|
14494
|
-
|
|
14571
|
+
const textChannel = await this.getTextChannel(channelId);
|
|
14572
|
+
const webhooks = await textChannel.fetchWebhooks();
|
|
14573
|
+
this.webhook = webhooks.find((h3) => h3.name === this.name && h3.owner?.id == this.client.user?.id) ?? await textChannel.createWebhook({
|
|
14495
14574
|
name: this.name,
|
|
14496
|
-
avatar: this.
|
|
14575
|
+
avatar: await this.getAvatar(),
|
|
14497
14576
|
reason: "Auto-created by WebhookManager"
|
|
14498
14577
|
});
|
|
14499
|
-
|
|
14578
|
+
Bot.log.debug(`Webhook ${this.webhook.id} ready for channel ${channelId}`);
|
|
14500
14579
|
return this.webhook;
|
|
14501
14580
|
} catch (error) {
|
|
14502
|
-
|
|
14581
|
+
Bot.log.error(`Failed to setup webhook for ${channelId}: ${error}`);
|
|
14503
14582
|
throw error;
|
|
14504
14583
|
}
|
|
14505
14584
|
}
|
|
14506
|
-
async send(content) {
|
|
14507
|
-
const webhook = await this.getWebhook();
|
|
14508
|
-
|
|
14585
|
+
async send(channelId, content) {
|
|
14586
|
+
const webhook = await this.getWebhook(channelId);
|
|
14587
|
+
let options = {};
|
|
14509
14588
|
if (SendableComponentBuilder.isSendableComponent(content)) {
|
|
14510
|
-
|
|
14511
|
-
|
|
14512
|
-
options.components = t3.components;
|
|
14513
|
-
} else if (typeof content == "string") {
|
|
14589
|
+
options = SendableComponentBuilder.buildMessage(content);
|
|
14590
|
+
} else if (typeof content === "string") {
|
|
14514
14591
|
options.content = content;
|
|
14515
14592
|
} else if (typeof content === "object") {
|
|
14516
14593
|
Object.assign(options, content);
|
|
14517
14594
|
} else {
|
|
14518
|
-
options.content = content;
|
|
14519
|
-
}
|
|
14520
|
-
if (this.channel instanceof ThreadChannel2) {
|
|
14521
|
-
options.threadId = this.channel.id;
|
|
14595
|
+
options.content = String(content);
|
|
14522
14596
|
}
|
|
14523
14597
|
try {
|
|
14524
|
-
|
|
14525
|
-
Log.info(`Webhook sent to ${this.channel.id}: ${content}`);
|
|
14526
|
-
return message;
|
|
14598
|
+
return await webhook.send(options);
|
|
14527
14599
|
} catch (error) {
|
|
14528
|
-
|
|
14600
|
+
Bot.log.error(`Webhook send failed to ${channelId}: ${error}`);
|
|
14529
14601
|
return null;
|
|
14530
14602
|
}
|
|
14531
14603
|
}
|
|
14532
14604
|
/**
|
|
14533
14605
|
* Quick success embed
|
|
14534
14606
|
*/
|
|
14535
|
-
async success(message) {
|
|
14536
|
-
return await this.send(EmbedManager.success(message));
|
|
14607
|
+
async success(channelId, message) {
|
|
14608
|
+
return await this.send(channelId, EmbedManager.success(message));
|
|
14537
14609
|
}
|
|
14538
14610
|
/**
|
|
14539
14611
|
* Quick error embed
|
|
14540
14612
|
*/
|
|
14541
|
-
async error(message) {
|
|
14542
|
-
return await this.send(EmbedManager.error(message));
|
|
14613
|
+
async error(channelId, message) {
|
|
14614
|
+
return await this.send(channelId, EmbedManager.error(message));
|
|
14543
14615
|
}
|
|
14544
14616
|
/**
|
|
14545
14617
|
* Delete webhook
|
|
14546
14618
|
*/
|
|
14547
|
-
async delete(reason) {
|
|
14619
|
+
async delete(channelId, reason) {
|
|
14548
14620
|
if (!this.webhook) return;
|
|
14549
14621
|
try {
|
|
14550
14622
|
await this.webhook.delete(reason ?? "Deleted by WebhookManager");
|
|
14551
|
-
|
|
14623
|
+
Bot.log.info(`Webhook ${this.webhook.id} deleted from ${channelId}`);
|
|
14552
14624
|
} catch (error) {
|
|
14553
14625
|
if (error.message.includes("Unknown Webhook")) {
|
|
14554
|
-
|
|
14626
|
+
Bot.log.warn(`Webhook already deleted from ${channelId}`);
|
|
14555
14627
|
} else {
|
|
14556
|
-
|
|
14628
|
+
Bot.log.error(`Failed to delete webhook from ${channelId}: ${error}`);
|
|
14557
14629
|
}
|
|
14558
14630
|
} finally {
|
|
14559
14631
|
this.webhook = null;
|
|
@@ -14859,11 +14931,7 @@ var ReactionManager = class {
|
|
|
14859
14931
|
};
|
|
14860
14932
|
|
|
14861
14933
|
// src/manager/guild/GuildManager.ts
|
|
14862
|
-
import {
|
|
14863
|
-
Guild as Guild3,
|
|
14864
|
-
VoiceChannel as VoiceChannel2,
|
|
14865
|
-
StageChannel as StageChannel2
|
|
14866
|
-
} from "discord.js";
|
|
14934
|
+
import { Guild as Guild2, StageChannel as StageChannel2, VoiceChannel as VoiceChannel2 } from "discord.js";
|
|
14867
14935
|
|
|
14868
14936
|
// src/manager/direct/BasicUserManager.ts
|
|
14869
14937
|
import { GuildMember as GuildMember2 } from "discord.js";
|
|
@@ -14938,22 +15006,9 @@ var BasicUserManager = class {
|
|
|
14938
15006
|
};
|
|
14939
15007
|
|
|
14940
15008
|
// src/manager/guild/GuildUserManager.ts
|
|
14941
|
-
import { Guild as Guild2 } from "discord.js";
|
|
14942
15009
|
import { setTimeout as setTimeout2 } from "timers/promises";
|
|
14943
15010
|
var MAX_NICKNAME_LENGTH = 32;
|
|
14944
15011
|
var GuildUserManager = class extends BasicUserManager {
|
|
14945
|
-
static async find(userId, guild) {
|
|
14946
|
-
try {
|
|
14947
|
-
if (guild instanceof Guild2) {
|
|
14948
|
-
return await guild.members.fetch(userId);
|
|
14949
|
-
} else {
|
|
14950
|
-
return await (await GuildManager.find(guild)).members.fetch(userId);
|
|
14951
|
-
}
|
|
14952
|
-
} catch (error) {
|
|
14953
|
-
Log.error(`UserManager: Member ${userId} not found`);
|
|
14954
|
-
return null;
|
|
14955
|
-
}
|
|
14956
|
-
}
|
|
14957
15012
|
static async rename(member, nickname, maxAttempts = 3) {
|
|
14958
15013
|
if (nickname.length > MAX_NICKNAME_LENGTH) {
|
|
14959
15014
|
nickname = nickname.slice(0, MAX_NICKNAME_LENGTH);
|
|
@@ -15470,7 +15525,14 @@ var GuildManager = class {
|
|
|
15470
15525
|
return Array.from(Bot.client.guilds.cache.values());
|
|
15471
15526
|
}
|
|
15472
15527
|
static async find(guild_id) {
|
|
15473
|
-
|
|
15528
|
+
try {
|
|
15529
|
+
const cached = Bot.client.guilds.cache.get(guild_id);
|
|
15530
|
+
if (cached) return cached;
|
|
15531
|
+
return await Bot.client.guilds.fetch(guild_id);
|
|
15532
|
+
} catch (error) {
|
|
15533
|
+
Log.error(`GuildManager: Guild ${guild_id} : ${error} `);
|
|
15534
|
+
return null;
|
|
15535
|
+
}
|
|
15474
15536
|
}
|
|
15475
15537
|
/**
|
|
15476
15538
|
* Search channel by ID (TextChannel, DMChannel, ThreadChannel)
|
|
@@ -15509,7 +15571,7 @@ var GuildManager = class {
|
|
|
15509
15571
|
*/
|
|
15510
15572
|
static async fetchAllMembers(guildId, MAX_ATTEMPTS = 3, RETRY_DELAY = Time.minute.MIN_05.toMilliseconds()) {
|
|
15511
15573
|
let guild;
|
|
15512
|
-
if (guildId instanceof
|
|
15574
|
+
if (guildId instanceof Guild2) {
|
|
15513
15575
|
guild = guildId;
|
|
15514
15576
|
} else {
|
|
15515
15577
|
let tmp = Bot.client.guilds.cache.get(guildId);
|
|
@@ -16061,8 +16123,8 @@ var SimpleMutex = class {
|
|
|
16061
16123
|
*/
|
|
16062
16124
|
async lock() {
|
|
16063
16125
|
if (this._locked) {
|
|
16064
|
-
return new Promise((
|
|
16065
|
-
this.queue.push(
|
|
16126
|
+
return new Promise((resolve2) => {
|
|
16127
|
+
this.queue.push(resolve2);
|
|
16066
16128
|
});
|
|
16067
16129
|
}
|
|
16068
16130
|
this._locked = true;
|
|
@@ -16089,7 +16151,7 @@ var SimpleMutex = class {
|
|
|
16089
16151
|
// package.json
|
|
16090
16152
|
var package_default = {
|
|
16091
16153
|
name: "@spatulox/simplediscordbot",
|
|
16092
|
-
version: "
|
|
16154
|
+
version: "2.0.0",
|
|
16093
16155
|
author: "Spatulox",
|
|
16094
16156
|
description: "Simple discord bot framework to set up a bot under 30 secondes",
|
|
16095
16157
|
exports: {
|