@seedcord/core 0.1.0-next.6 → 0.1.0-next.8
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/dist/HmrModuleHandler-3sNgKHdf.mjs +163 -0
- package/dist/HmrModuleHandler-3sNgKHdf.mjs.map +1 -0
- package/dist/HmrModuleHandler-CTBng7wV.cjs +170 -0
- package/dist/HmrModuleHandler-CTBng7wV.cjs.map +1 -0
- package/dist/Plugin-BZit5HUI.d.mts +555 -0
- package/dist/{Plugin-C2-VHrsX.cjs → Plugin-BlkhHNRm.cjs} +15 -34
- package/dist/Plugin-BlkhHNRm.cjs.map +1 -0
- package/dist/{Plugin-PcdPjAzc.mjs → Plugin-CDAV7P9l.mjs} +16 -29
- package/dist/Plugin-CDAV7P9l.mjs.map +1 -0
- package/dist/basic-1hebYVcN.d.mts +22 -0
- package/dist/contextMenuLeaves-f2rbyo83.d.mts +19 -0
- package/dist/{permissions-DSW_EZfN.cjs → cursor-BMkFAwO2.cjs} +308 -300
- package/dist/cursor-BMkFAwO2.cjs.map +1 -0
- package/dist/{permissions-RVCBhL2n.mjs → cursor-BvSH8tgw.mjs} +249 -247
- package/dist/cursor-BvSH8tgw.mjs.map +1 -0
- package/dist/{AutocompleteOptions-eKhIe6Qt.d.mts → cursor-D6nBjwaE.d.mts} +207 -116
- package/dist/hmr.index.cjs +2 -164
- package/dist/hmr.index.mjs +2 -162
- package/dist/index-Cr4-VV4u.d.mts +142 -0
- package/dist/index.cjs +362 -63
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.mts +239 -38
- package/dist/index.mjs +313 -26
- package/dist/index.mjs.map +1 -1
- package/dist/internal.index.cjs +278 -83
- package/dist/internal.index.cjs.map +1 -1
- package/dist/internal.index.d.mts +111 -42
- package/dist/internal.index.mjs +223 -43
- package/dist/internal.index.mjs.map +1 -1
- package/dist/node-internal.index.cjs +314 -76
- package/dist/node-internal.index.cjs.map +1 -1
- package/dist/node-internal.index.d.mts +123 -2164
- package/dist/node-internal.index.mjs +313 -77
- package/dist/node-internal.index.mjs.map +1 -1
- package/dist/{phases-BfpAG6w3.mjs → phases-BauKJOTT.mjs} +2 -2
- package/dist/phases-BauKJOTT.mjs.map +1 -0
- package/dist/{phases-C_BGNyVo.cjs → phases-DcuDHoQl.cjs} +2 -2
- package/dist/phases-DcuDHoQl.cjs.map +1 -0
- package/dist/plugin.index.cjs +1 -1
- package/dist/plugin.index.d.mts +2 -2
- package/dist/plugin.index.mjs +1 -1
- package/dist/publishDefault-CVlwYUS5.cjs +382 -0
- package/dist/publishDefault-CVlwYUS5.cjs.map +1 -0
- package/dist/publishDefault-CldnxcT2.mjs +287 -0
- package/dist/publishDefault-CldnxcT2.mjs.map +1 -0
- package/dist/slashRouteLeaves-BANDtPFm.mjs +23 -0
- package/dist/slashRouteLeaves-BANDtPFm.mjs.map +1 -0
- package/dist/slashRouteLeaves-nfxOAM7Q.cjs +28 -0
- package/dist/slashRouteLeaves-nfxOAM7Q.cjs.map +1 -0
- package/dist/subscribers-BSJoyKNN.cjs +517 -0
- package/dist/subscribers-BSJoyKNN.cjs.map +1 -0
- package/dist/subscribers-DuxdM2cS.mjs +480 -0
- package/dist/subscribers-DuxdM2cS.mjs.map +1 -0
- package/package.json +7 -6
- package/dist/Plugin-C2-VHrsX.cjs.map +0 -1
- package/dist/Plugin-CNyRKDHT.d.mts +0 -226
- package/dist/Plugin-PcdPjAzc.mjs.map +0 -1
- package/dist/hmr.index.cjs.map +0 -1
- package/dist/hmr.index.mjs.map +0 -1
- package/dist/is-never-Ddaba1Su.d.mts +0 -58
- package/dist/permissions-DSW_EZfN.cjs.map +0 -1
- package/dist/permissions-RVCBhL2n.mjs.map +0 -1
- package/dist/phases-BfpAG6w3.mjs.map +0 -1
- package/dist/phases-C_BGNyVo.cjs.map +0 -1
|
@@ -1,45 +1,173 @@
|
|
|
1
|
+
import { d as InteractionRouteKeys, f as InteractionRoutes, g as contextMenuLeaves, i as BuilderComponent, u as InteractionMetadataKey } from "./publishDefault-CldnxcT2.mjs";
|
|
1
2
|
import "reflect-metadata";
|
|
3
|
+
import { SlashCommandBuilder, TextDisplayBuilder } from "@discordjs/builders";
|
|
4
|
+
import { Logger, paint } from "@seedcord/logger";
|
|
5
|
+
import { routeLeavesOf } from "@seedcord/utils/internal";
|
|
6
|
+
import { ApplicationCommandType, PermissionFlagsBits } from "discord-api-types/v10";
|
|
2
7
|
import { SeedcordErrorCode } from "@seedcord/errors";
|
|
3
|
-
import { SeedcordError, SeedcordRangeError
|
|
4
|
-
import { ApplicationCommandType, InteractionContextType, PermissionFlagsBits } from "discord-api-types/v10";
|
|
5
|
-
import { ActionRowBuilder, ButtonBuilder, ChannelSelectMenuBuilder, CheckboxBuilder, CheckboxGroupBuilder, CheckboxGroupOptionBuilder, ContainerBuilder, ContextMenuCommandBuilder, EmbedBuilder, FileBuilder, FileUploadBuilder, LabelBuilder, MediaGalleryBuilder, MentionableSelectMenuBuilder, ModalBuilder, RadioGroupBuilder, RadioGroupOptionBuilder, RoleSelectMenuBuilder, SectionBuilder, SeparatorBuilder, SlashCommandBuilder, SlashCommandSubcommandBuilder, SlashCommandSubcommandGroupBuilder, StringSelectMenuBuilder, StringSelectMenuOptionBuilder, TextDisplayBuilder, TextInputBuilder, UserSelectMenuBuilder } from "@discordjs/builders";
|
|
8
|
+
import { SeedcordError, SeedcordRangeError } from "@seedcord/errors/internal";
|
|
6
9
|
import { prettify, toEpochSeconds } from "@seedcord/utils";
|
|
7
10
|
|
|
8
|
-
//#region src/
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
11
|
+
//#region src/miscellaneous/guarded.ts
|
|
12
|
+
/**
|
|
13
|
+
* A backing record for a generated accessor. Null-prototype, on a plain object a key named `__proto__` sets
|
|
14
|
+
* the store's prototype and adds no entry.
|
|
15
|
+
*
|
|
16
|
+
* @internal
|
|
17
|
+
*/
|
|
18
|
+
function accessorStore() {
|
|
19
|
+
return Object.create(null);
|
|
20
|
+
}
|
|
21
|
+
/** Empties a store in place, keeping the reference the accessor's Proxy wraps. @internal */
|
|
22
|
+
function clearStore(store) {
|
|
23
|
+
for (const key of Object.keys(store)) Reflect.deleteProperty(store, key);
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Wraps a generated accessor's backing record so a read of an absent key throws. Handler modules import before
|
|
27
|
+
* startup fills the record, and an unguarded read there returns `undefined` and renders as an empty string.
|
|
28
|
+
*
|
|
29
|
+
* @internal
|
|
30
|
+
*/
|
|
31
|
+
function guardedAccessor(accessor, storage) {
|
|
32
|
+
return new Proxy(storage, { get(target, key, receiver) {
|
|
33
|
+
if (typeof key !== "string" || Object.hasOwn(target, key)) return Reflect.get(target, key, receiver);
|
|
34
|
+
throw new SeedcordError(SeedcordErrorCode.CoreAccessorUnresolved, [accessor, key]);
|
|
35
|
+
} });
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
//#endregion
|
|
39
|
+
//#region src/commands/CommandInjector.ts
|
|
40
|
+
const commandStorage = accessorStore();
|
|
41
|
+
const userMenuStorage = accessorStore();
|
|
42
|
+
const messageMenuStorage = accessorStore();
|
|
43
|
+
/**
|
|
44
|
+
* The bot's deployed slash commands, keyed by {@link SlashOptionRegistry}. Filled by
|
|
45
|
+
* {@link CommandInjector} after each deploy, and a read before that throws.
|
|
46
|
+
*
|
|
47
|
+
* @example
|
|
48
|
+
* ```ts
|
|
49
|
+
* import { Commands } from '@seedcord/gateway';
|
|
50
|
+
*
|
|
51
|
+
* await this.reply(`Try ${Commands['config/set'].mention}`);
|
|
52
|
+
*
|
|
53
|
+
* // a help listing
|
|
54
|
+
* const lines = Object.values(Commands).map((c) => `${c.mention} ${c.description}`);
|
|
55
|
+
* ```
|
|
56
|
+
*/
|
|
57
|
+
const Commands = guardedAccessor("Commands", commandStorage);
|
|
58
|
+
/**
|
|
59
|
+
* The bot's deployed context-menu commands. Filled by {@link CommandInjector} after each deploy, and a read
|
|
60
|
+
* before that throws.
|
|
61
|
+
*
|
|
62
|
+
* @example
|
|
63
|
+
* ```ts
|
|
64
|
+
* import { ContextMenus } from '@seedcord/gateway';
|
|
65
|
+
*
|
|
66
|
+
* const id = ContextMenus.user['View Profile'].id;
|
|
67
|
+
* ```
|
|
68
|
+
*/
|
|
69
|
+
const ContextMenus = {
|
|
70
|
+
user: guardedAccessor("ContextMenus.user", userMenuStorage),
|
|
71
|
+
message: guardedAccessor("ContextMenus.message", messageMenuStorage)
|
|
72
|
+
};
|
|
73
|
+
const MULTI_GUILD = Symbol("seedcord:commands:multi-guild");
|
|
74
|
+
function commandKey(type, name) {
|
|
75
|
+
return `${type}:${name}`;
|
|
76
|
+
}
|
|
77
|
+
function slashBuildersOf(all) {
|
|
78
|
+
const slash = all.filter((command) => command instanceof SlashCommandBuilder);
|
|
79
|
+
return [...new Set(slash)];
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Records each deployed command on {@link Commands} and {@link ContextMenus}.
|
|
83
|
+
*
|
|
84
|
+
* @internal
|
|
85
|
+
*/
|
|
86
|
+
var CommandInjector = class {
|
|
87
|
+
logger = new Logger("Commands", { channel: "bot" });
|
|
88
|
+
inject(deploy, all) {
|
|
89
|
+
this.clear();
|
|
90
|
+
const ids = {
|
|
91
|
+
global: this.indexByKey(deploy.global),
|
|
92
|
+
guild: this.indexGuilds(deploy.guilds),
|
|
93
|
+
warned: /* @__PURE__ */ new Set()
|
|
94
|
+
};
|
|
95
|
+
let clickable = 0;
|
|
96
|
+
for (const command of slashBuildersOf(all)) {
|
|
97
|
+
const id = this.resolveId(ApplicationCommandType.ChatInput, command.name, ids, "falling back to plain text (not clickable)");
|
|
98
|
+
for (const leaf of routeLeavesOf(command.toJSON())) {
|
|
99
|
+
commandStorage[leaf.route] = {
|
|
100
|
+
mention: id ? this.toMention(leaf.route, id) : this.toPlain(leaf.route),
|
|
101
|
+
...id && { id },
|
|
102
|
+
route: leaf.route,
|
|
103
|
+
description: leaf.description
|
|
104
|
+
};
|
|
105
|
+
if (id) clickable++;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
const menus = contextMenuLeaves(all);
|
|
109
|
+
this.injectMenus(menus.user, ApplicationCommandType.User, userMenuStorage, ids);
|
|
110
|
+
this.injectMenus(menus.message, ApplicationCommandType.Message, messageMenuStorage, ids);
|
|
111
|
+
this.logger.utils.summary("Linked commands", {
|
|
112
|
+
clickable,
|
|
113
|
+
plain: Object.keys(commandStorage).length - clickable,
|
|
114
|
+
"context menus": menus.user.size + menus.message.size
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
injectMenus(names, kind, storage, ids) {
|
|
118
|
+
for (const name of names) {
|
|
119
|
+
const id = this.resolveId(kind, name, ids, "leaving its id unset");
|
|
120
|
+
storage[name] = {
|
|
121
|
+
...id && { id },
|
|
122
|
+
name,
|
|
123
|
+
kind
|
|
124
|
+
};
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
indexByKey(collection) {
|
|
128
|
+
const map = /* @__PURE__ */ new Map();
|
|
129
|
+
for (const command of collection.values()) map.set(commandKey(command.type, command.name), command.id);
|
|
130
|
+
return map;
|
|
131
|
+
}
|
|
132
|
+
indexGuilds(guilds) {
|
|
133
|
+
const map = /* @__PURE__ */ new Map();
|
|
134
|
+
for (const collection of guilds.values()) for (const command of collection.values()) {
|
|
135
|
+
const key = commandKey(command.type, command.name);
|
|
136
|
+
const existing = map.get(key);
|
|
137
|
+
if (existing === void 0) map.set(key, command.id);
|
|
138
|
+
else if (existing !== command.id) map.set(key, MULTI_GUILD);
|
|
139
|
+
}
|
|
140
|
+
return map;
|
|
141
|
+
}
|
|
142
|
+
resolveId(type, name, ids, consequence) {
|
|
143
|
+
const key = commandKey(type, name);
|
|
144
|
+
const global = ids.global.get(key);
|
|
145
|
+
if (global) return global;
|
|
146
|
+
const guild = ids.guild.get(key);
|
|
147
|
+
if (guild === void 0) return void 0;
|
|
148
|
+
if (guild === MULTI_GUILD) {
|
|
149
|
+
if (!ids.warned.has(key)) {
|
|
150
|
+
this.logger.warn(`${paint.sky.bold(name)} is deployed to multiple guilds, ${consequence}.`);
|
|
151
|
+
ids.warned.add(key);
|
|
152
|
+
}
|
|
153
|
+
return;
|
|
154
|
+
}
|
|
155
|
+
return guild;
|
|
156
|
+
}
|
|
157
|
+
toMention(route, id) {
|
|
158
|
+
return `</${route.replaceAll("/", " ")}:${id}>`;
|
|
159
|
+
}
|
|
160
|
+
toPlain(route) {
|
|
161
|
+
return `/${route.replaceAll("/", " ")}`;
|
|
162
|
+
}
|
|
163
|
+
clear() {
|
|
164
|
+
for (const store of [
|
|
165
|
+
commandStorage,
|
|
166
|
+
userMenuStorage,
|
|
167
|
+
messageMenuStorage
|
|
168
|
+
]) clearStore(store);
|
|
169
|
+
}
|
|
36
170
|
};
|
|
37
|
-
const MiddlewareMetadataKey = Symbol("seedcord:middleware:metadata");
|
|
38
|
-
const EventMetadataKey = Symbol("seedcord:event:metadata");
|
|
39
|
-
const CommandMetadataKey = Symbol("seedcord:command:metadata");
|
|
40
|
-
const GatedMetadataKey = Symbol("seedcord:gated:metadata");
|
|
41
|
-
const SubscribeMetadataKey = Symbol("seedcord:subscribe:metadata");
|
|
42
|
-
const WebhookUrlMetadataKey = Symbol("seedcord:webhookUrl:metadata");
|
|
43
171
|
|
|
44
172
|
//#endregion
|
|
45
173
|
//#region src/stops/Notice.ts
|
|
@@ -107,202 +235,6 @@ var Notice = class extends Error {
|
|
|
107
235
|
}
|
|
108
236
|
};
|
|
109
237
|
|
|
110
|
-
//#endregion
|
|
111
|
-
//#region src/components/botColorHolder.ts
|
|
112
|
-
const DEFAULT_COLOR = "Default";
|
|
113
|
-
let current = DEFAULT_COLOR;
|
|
114
|
-
function setBotColor(color) {
|
|
115
|
-
current = color ?? DEFAULT_COLOR;
|
|
116
|
-
}
|
|
117
|
-
function getBotColor() {
|
|
118
|
-
return current;
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
//#endregion
|
|
122
|
-
//#region src/components/builderTypes.ts
|
|
123
|
-
/**
|
|
124
|
-
* Available Discord.js builder classes for use with BuilderComponent for commands, embeds, modals, etc.
|
|
125
|
-
*
|
|
126
|
-
* @internal
|
|
127
|
-
*/
|
|
128
|
-
const BuilderTypes = {
|
|
129
|
-
command: SlashCommandBuilder,
|
|
130
|
-
context_menu: ContextMenuCommandBuilder,
|
|
131
|
-
subcommand: SlashCommandSubcommandBuilder,
|
|
132
|
-
group: SlashCommandSubcommandGroupBuilder,
|
|
133
|
-
embed: EmbedBuilder,
|
|
134
|
-
modal: ModalBuilder,
|
|
135
|
-
label: LabelBuilder,
|
|
136
|
-
text_input: TextInputBuilder,
|
|
137
|
-
file_upload: FileUploadBuilder,
|
|
138
|
-
checkbox: CheckboxBuilder,
|
|
139
|
-
checkbox_group: CheckboxGroupBuilder,
|
|
140
|
-
checkbox_group_option: CheckboxGroupOptionBuilder,
|
|
141
|
-
radio_group: RadioGroupBuilder,
|
|
142
|
-
radio_group_option: RadioGroupOptionBuilder,
|
|
143
|
-
button: ButtonBuilder,
|
|
144
|
-
menu_string: StringSelectMenuBuilder,
|
|
145
|
-
menu_option_string: StringSelectMenuOptionBuilder,
|
|
146
|
-
menu_user: UserSelectMenuBuilder,
|
|
147
|
-
menu_channel: ChannelSelectMenuBuilder,
|
|
148
|
-
menu_mentionable: MentionableSelectMenuBuilder,
|
|
149
|
-
menu_role: RoleSelectMenuBuilder,
|
|
150
|
-
container: ContainerBuilder,
|
|
151
|
-
text_display: TextDisplayBuilder,
|
|
152
|
-
file: FileBuilder,
|
|
153
|
-
media: MediaGalleryBuilder,
|
|
154
|
-
section: SectionBuilder,
|
|
155
|
-
separator: SeparatorBuilder
|
|
156
|
-
};
|
|
157
|
-
/**
|
|
158
|
-
* Available Discord.js action row classes for use with RowComponent for Select Menus and Buttons
|
|
159
|
-
*
|
|
160
|
-
* @internal
|
|
161
|
-
*/
|
|
162
|
-
const RowTypes = {
|
|
163
|
-
button: ActionRowBuilder,
|
|
164
|
-
menu_string: ActionRowBuilder,
|
|
165
|
-
menu_user: ActionRowBuilder,
|
|
166
|
-
menu_channel: ActionRowBuilder,
|
|
167
|
-
menu_mentionable: ActionRowBuilder,
|
|
168
|
-
menu_role: ActionRowBuilder
|
|
169
|
-
};
|
|
170
|
-
|
|
171
|
-
//#endregion
|
|
172
|
-
//#region src/components/colors.ts
|
|
173
|
-
const Colors = {
|
|
174
|
-
Aqua: 1752220,
|
|
175
|
-
Blue: 3447003,
|
|
176
|
-
Blurple: 5793266,
|
|
177
|
-
DarkAqua: 1146986,
|
|
178
|
-
DarkBlue: 2123412,
|
|
179
|
-
DarkButNotBlack: 2895667,
|
|
180
|
-
DarkerGrey: 8359053,
|
|
181
|
-
DarkGold: 12745742,
|
|
182
|
-
DarkGreen: 2067276,
|
|
183
|
-
DarkGrey: 9936031,
|
|
184
|
-
DarkNavy: 2899536,
|
|
185
|
-
DarkOrange: 11027200,
|
|
186
|
-
DarkPurple: 7419530,
|
|
187
|
-
DarkRed: 10038562,
|
|
188
|
-
DarkVividPink: 11342935,
|
|
189
|
-
Default: 0,
|
|
190
|
-
Fuchsia: 15418782,
|
|
191
|
-
Gold: 15844367,
|
|
192
|
-
Green: 5763719,
|
|
193
|
-
Grey: 9807270,
|
|
194
|
-
Greyple: 10070709,
|
|
195
|
-
LightGrey: 12370112,
|
|
196
|
-
LuminousVividPink: 15277667,
|
|
197
|
-
Navy: 3426654,
|
|
198
|
-
NotQuiteBlack: 2303786,
|
|
199
|
-
Orange: 15105570,
|
|
200
|
-
Purple: 10181046,
|
|
201
|
-
Red: 15548997,
|
|
202
|
-
White: 16777215,
|
|
203
|
-
Yellow: 16705372
|
|
204
|
-
};
|
|
205
|
-
|
|
206
|
-
//#endregion
|
|
207
|
-
//#region src/components/resolveColor.ts
|
|
208
|
-
const MAX_COLOR = 16777215;
|
|
209
|
-
const RED_SHIFT = 16;
|
|
210
|
-
const GREEN_SHIFT = 8;
|
|
211
|
-
const palette = Colors;
|
|
212
|
-
/**
|
|
213
|
-
* Resolves a {@link BotColor} to the integer Discord expects.
|
|
214
|
-
*
|
|
215
|
-
* Ported from discord.js (Apache-2.0), `resolveColor` in src/util/Util.js.
|
|
216
|
-
*/
|
|
217
|
-
function resolveColor(color) {
|
|
218
|
-
let resolved;
|
|
219
|
-
if (typeof color === "string") {
|
|
220
|
-
if (color === "Random") return Math.floor(Math.random() * 16777216);
|
|
221
|
-
if (color === "Default") return 0;
|
|
222
|
-
if (/^#?[\da-f]{6}$/i.test(color)) return Number.parseInt(color.replace("#", ""), 16);
|
|
223
|
-
resolved = palette[color];
|
|
224
|
-
} else if (typeof color === "number") resolved = color;
|
|
225
|
-
else resolved = (color[0] << RED_SHIFT) + (color[1] << GREEN_SHIFT) + color[2];
|
|
226
|
-
if (resolved === void 0 || !Number.isSafeInteger(resolved)) throw new SeedcordTypeError(SeedcordErrorCode.ColorUnresolvable, [JSON.stringify(color)]);
|
|
227
|
-
if (resolved < 0 || resolved > MAX_COLOR) throw new SeedcordRangeError(SeedcordErrorCode.ColorOutOfRange);
|
|
228
|
-
return resolved;
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
//#endregion
|
|
232
|
-
//#region src/components/Component.ts
|
|
233
|
-
/**
|
|
234
|
-
* Base class for Discord component wrappers.
|
|
235
|
-
*
|
|
236
|
-
* @typeParam TComponent - The Discord.js component type being wrapped
|
|
237
|
-
*
|
|
238
|
-
* @internal
|
|
239
|
-
*/
|
|
240
|
-
var BaseComponent = class {
|
|
241
|
-
_component;
|
|
242
|
-
constructor(ComponentClass) {
|
|
243
|
-
this._component = new ComponentClass();
|
|
244
|
-
}
|
|
245
|
-
/**
|
|
246
|
-
* The wrapped builder, for calling Discord.js methods like setTitle() and setDescription() inside a subclass.
|
|
247
|
-
*
|
|
248
|
-
* @example this.instance.setTitle('My Modal')
|
|
249
|
-
*/
|
|
250
|
-
get instance() {
|
|
251
|
-
return this._component;
|
|
252
|
-
}
|
|
253
|
-
};
|
|
254
|
-
/**
|
|
255
|
-
* Base class for Discord.js builder components
|
|
256
|
-
*
|
|
257
|
-
* Wraps Discord.js builders (SlashCommandBuilder, EmbedBuilder, etc.) with
|
|
258
|
-
* Seedcord-specific defaults and helper methods.
|
|
259
|
-
*
|
|
260
|
-
* @typeParam BuilderKey - The type of Discord.js builder being wrapped
|
|
261
|
-
*/
|
|
262
|
-
var BuilderComponent = class extends BaseComponent {
|
|
263
|
-
type;
|
|
264
|
-
colorApplied = false;
|
|
265
|
-
constructor(type) {
|
|
266
|
-
const ComponentClass = BuilderTypes[type];
|
|
267
|
-
super(ComponentClass);
|
|
268
|
-
this.type = type;
|
|
269
|
-
if (this.instance instanceof SlashCommandBuilder || this.instance instanceof ContextMenuCommandBuilder) this.instance.setContexts(InteractionContextType.Guild);
|
|
270
|
-
}
|
|
271
|
-
get component() {
|
|
272
|
-
this.applyBotColor();
|
|
273
|
-
return this.instance;
|
|
274
|
-
}
|
|
275
|
-
applyBotColor() {
|
|
276
|
-
if (this.colorApplied) return;
|
|
277
|
-
this.colorApplied = true;
|
|
278
|
-
const color = getBotColor();
|
|
279
|
-
if (this.instance instanceof EmbedBuilder) {
|
|
280
|
-
if (this.instance.data.color === void 0) this.instance.setColor(resolveColor(color));
|
|
281
|
-
} else if (this.instance instanceof ContainerBuilder) {
|
|
282
|
-
const accent = this.instance.data.accent_color;
|
|
283
|
-
if (accent === null || accent === void 0) this.instance.setAccentColor(color === "Default" ? void 0 : resolveColor(color));
|
|
284
|
-
}
|
|
285
|
-
}
|
|
286
|
-
};
|
|
287
|
-
/**
|
|
288
|
-
* Base class for Discord action row components
|
|
289
|
-
*
|
|
290
|
-
* Wraps Discord.js action row builder with Seedcord-specific defaults and helper methods.
|
|
291
|
-
*
|
|
292
|
-
* @typeParam RowKey - The Discord.js action row type being wrapped
|
|
293
|
-
*/
|
|
294
|
-
var RowComponent = class extends BaseComponent {
|
|
295
|
-
type;
|
|
296
|
-
constructor(type) {
|
|
297
|
-
const ComponentClass = RowTypes[type];
|
|
298
|
-
super(ComponentClass);
|
|
299
|
-
this.type = type;
|
|
300
|
-
}
|
|
301
|
-
get component() {
|
|
302
|
-
return this.instance;
|
|
303
|
-
}
|
|
304
|
-
};
|
|
305
|
-
|
|
306
238
|
//#endregion
|
|
307
239
|
//#region src/stops/NoticeCard.ts
|
|
308
240
|
/**
|
|
@@ -955,6 +887,21 @@ var MissingPermissions = class extends Notice {
|
|
|
955
887
|
return { components: [new NoticeCard(`${this.customLead ?? `${this.subject === null ? "You are" : `${this.subject} is`} missing the following permission entries:`}\n\n${bullets}`).component] };
|
|
956
888
|
}
|
|
957
889
|
};
|
|
890
|
+
var HasDangerousPermissions = class extends Notice {
|
|
891
|
+
subject;
|
|
892
|
+
dangerousPerms;
|
|
893
|
+
customLead;
|
|
894
|
+
constructor(message, subject, dangerousPerms) {
|
|
895
|
+
super(message ?? "A dangerous permission is enabled.");
|
|
896
|
+
this.subject = subject;
|
|
897
|
+
this.dangerousPerms = dangerousPerms;
|
|
898
|
+
this.customLead = message;
|
|
899
|
+
}
|
|
900
|
+
render() {
|
|
901
|
+
const bullets = this.dangerousPerms.map((perm) => `• ${perm}`).join("\n");
|
|
902
|
+
return { components: [new NoticeCard(`${this.customLead ?? `${this.subject} has the following permission entries that must not be enabled:`}\n\n${bullets}`).component] };
|
|
903
|
+
}
|
|
904
|
+
};
|
|
958
905
|
|
|
959
906
|
//#endregion
|
|
960
907
|
//#region src/gates/effects.ts
|
|
@@ -995,10 +942,37 @@ function pickNotice(options, makeDefault) {
|
|
|
995
942
|
}
|
|
996
943
|
|
|
997
944
|
//#endregion
|
|
998
|
-
//#region src/
|
|
999
|
-
/** Permission bit to its prettified human-readable name
|
|
945
|
+
//#region src/permissions/bits.ts
|
|
946
|
+
/** Permission bit to its prettified human-readable name. */
|
|
1000
947
|
const PermissionNames = new Map(Object.entries(PermissionFlagsBits).map(([key, bit]) => [bit, prettify(key)]));
|
|
1001
948
|
const ADMINISTRATOR = PermissionFlagsBits.Administrator;
|
|
949
|
+
function nameOf(bit) {
|
|
950
|
+
return PermissionNames.get(bit) ?? String(bit);
|
|
951
|
+
}
|
|
952
|
+
function holds(held, bit) {
|
|
953
|
+
return (held & ADMINISTRATOR) === ADMINISTRATOR || (held & bit) === bit;
|
|
954
|
+
}
|
|
955
|
+
/** @internal */
|
|
956
|
+
function hasAll(held, scope) {
|
|
957
|
+
return scope.every((bit) => holds(held, bit));
|
|
958
|
+
}
|
|
959
|
+
/** @internal only reached once hasAll failed, so the administrator bit is absent */
|
|
960
|
+
function missingNames(held, scope) {
|
|
961
|
+
return scope.reduce((names, bit) => {
|
|
962
|
+
if ((held & bit) !== bit) names.push(nameOf(bit));
|
|
963
|
+
return names;
|
|
964
|
+
}, []);
|
|
965
|
+
}
|
|
966
|
+
/** @internal */
|
|
967
|
+
function presentNames(held, scope) {
|
|
968
|
+
return scope.reduce((names, bit) => {
|
|
969
|
+
if (holds(held, bit)) names.push(nameOf(bit));
|
|
970
|
+
return names;
|
|
971
|
+
}, []);
|
|
972
|
+
}
|
|
973
|
+
|
|
974
|
+
//#endregion
|
|
975
|
+
//#region src/gates/catalog/permissions.ts
|
|
1002
976
|
const MEMBER_CHECK = {
|
|
1003
977
|
unresolved: "Your server member data could not be resolved. Try again.",
|
|
1004
978
|
subject: null
|
|
@@ -1007,16 +981,6 @@ const BOT_CHECK = {
|
|
|
1007
981
|
unresolved: "The bot's permissions could not be resolved. Try again.",
|
|
1008
982
|
subject: "The bot"
|
|
1009
983
|
};
|
|
1010
|
-
function hasAll(held, scope) {
|
|
1011
|
-
if ((held & ADMINISTRATOR) === ADMINISTRATOR) return true;
|
|
1012
|
-
return scope.every((bit) => (held & bit) === bit);
|
|
1013
|
-
}
|
|
1014
|
-
function missingNames(held, scope) {
|
|
1015
|
-
return scope.reduce((names, bit) => {
|
|
1016
|
-
if ((held & bit) !== bit) names.push(PermissionNames.get(bit) ?? String(bit));
|
|
1017
|
-
return names;
|
|
1018
|
-
}, []);
|
|
1019
|
-
}
|
|
1020
984
|
function refusePermissions(held, scope, options, guildId, kind) {
|
|
1021
985
|
if (held === null) throw pickNotice(options?.notInGuild, (message) => new NotInGuild(message ?? (guildId ? kind.unresolved : void 0)));
|
|
1022
986
|
if (hasAll(held, scope)) return;
|
|
@@ -1067,5 +1031,43 @@ function RequireRole(roleId, options) {
|
|
|
1067
1031
|
}
|
|
1068
1032
|
|
|
1069
1033
|
//#endregion
|
|
1070
|
-
|
|
1071
|
-
|
|
1034
|
+
//#region src/stops/Silence.ts
|
|
1035
|
+
/**
|
|
1036
|
+
* Throw to stop a handler with no reply and no report.
|
|
1037
|
+
*
|
|
1038
|
+
* The framework boundary catches `Silence` before {@link Notice}, makes zero Discord calls, and stops.
|
|
1039
|
+
* Ideally you'd only throw this in `EventHandlers` (or `Gates` for those), because it doesn't make sense to
|
|
1040
|
+
* leave the user with no reply for an interaction.
|
|
1041
|
+
*
|
|
1042
|
+
* @example
|
|
1043
|
+
* ```ts
|
|
1044
|
+
* import { Silence } from '@seedcord/gateway';
|
|
1045
|
+
*
|
|
1046
|
+
* // before any reply or defer, drop the interaction with no reply and no report
|
|
1047
|
+
* if (await isBlacklisted(interaction.user.id)) throw new Silence('blacklisted user');
|
|
1048
|
+
* ```
|
|
1049
|
+
*/
|
|
1050
|
+
var Silence = class extends Error {
|
|
1051
|
+
reason;
|
|
1052
|
+
/**
|
|
1053
|
+
* @param reason - Optional note written only to a debug log, never shown to the user or reported.
|
|
1054
|
+
*/
|
|
1055
|
+
constructor(reason) {
|
|
1056
|
+
super(reason ?? "Silence");
|
|
1057
|
+
this.reason = reason;
|
|
1058
|
+
Error.captureStackTrace(this, this.constructor);
|
|
1059
|
+
}
|
|
1060
|
+
};
|
|
1061
|
+
|
|
1062
|
+
//#endregion
|
|
1063
|
+
//#region src/pagination/cursor.ts
|
|
1064
|
+
const PAGE_MAX = 1e6;
|
|
1065
|
+
const SLOT_MAX = 4;
|
|
1066
|
+
/** Build the page cursor for a paginator. */
|
|
1067
|
+
function pageCursor(prefix) {
|
|
1068
|
+
return new CustomId(prefix).int("page", 0, PAGE_MAX).int("slot", 0, SLOT_MAX);
|
|
1069
|
+
}
|
|
1070
|
+
|
|
1071
|
+
//#endregion
|
|
1072
|
+
export { areRoutes as A, prefixOf as B, NotInDm as C, defineEffectGate as D, OnCooldown as E, storeInteractionRoute as F, ContextMenus as G, Notice as H, ComponentDefsKey as I, guardedAccessor as J, accessorStore as K, decodeComponentRoute as L, interactionRoutesOf as M, selectMenuRouteOf as N, defineGate as O, storeComponentRoute as P, CustomId as R, NotAllowed as S, NotOwner as T, CommandInjector as U, NoticeCard as V, Commands as W, GateNotice as _, RequirePermissions as a, MissingRole as b, hasAll as c, pickNotice as d, discardCommits as f, runCommits as g, runCheck as h, RequireBotPermissions as i, contextMenuRouteOf as j, SelectMenuKind as k, missingNames as l, rollbackCommits as m, pageCursor as n, RequireRole as o, markCommits as p, clearStore as q, Silence as r, PermissionNames as s, PAGE_MAX as t, presentNames as u, HasDangerousPermissions as v, NotInGuild as w, NeedsAny as x, MissingPermissions as y, decodeFor as z };
|
|
1073
|
+
//# sourceMappingURL=cursor-BvSH8tgw.mjs.map
|