WhacK
WhacK
Explore posts from servers
SIASapphire - Imagine a framework
Created by WhacK on 12/1/2024 in #sapphire-support
string-store not finding identifiers other than first in Schema on deserialize typescript
const deserialized = SidekickCustomIdStore.deserialize(interaction.customId).data as {
playerId: string;
characterSlot: number;
purchased: 0 | 1;
humanoid: boolean;
cr: number;
name: string;
creature: string;
};
const deserialized = SidekickCustomIdStore.deserialize(interaction.customId).data as {
playerId: string;
characterSlot: number;
purchased: 0 | 1;
humanoid: boolean;
cr: number;
name: string;
creature: string;
};
Seemed to fix it thanks
8 replies
SIASapphire - Imagine a framework
Created by WhacK on 12/1/2024 in #sapphire-support
string-store not finding identifiers other than first in Schema on deserialize typescript
Ok I'll try figuring that out. Thank you.
8 replies
SIASapphire - Imagine a framework
Created by WhacK on 12/1/2024 in #sapphire-support
string-store not finding identifiers other than first in Schema on deserialize typescript
when I hover it shows everything there, and the logger statements show it properly deserialized in the console
8 replies
SIASapphire - Imagine a framework
Created by WhacK on 12/1/2024 in #sapphire-support
string-store not finding identifiers other than first in Schema on deserialize typescript
export class SidekickRegisterCancelHandler extends InteractionHandler<{ interactionHandlerType: InteractionHandlerTypes.Button }> {
public async run(interaction: ButtonInteraction) {
try {
const player = await getPlayerByDiscordId(interaction.user.id);
if (isNullish(player)) {
throw new Error('Unable to retrieve player');
}
if (player.active_character && player.active_character.active) {
const deserialized = SidekickCustomIdStore.deserialize(interaction.customId).data;

// const registeredSidekick = await registerSidekickToCharacter(
// deserialized.playerId.toString(),
// deserialized.characterSlot,
// deserialized.name,
// SidekickTier[deserialized.cr],
// SidekickCreatureTypes[deserialized.creature],
// deserialized.purchased
// );

return interaction.editReply({ content: 'Sidekick registered', embeds: [], components: [] });
} else {
throw new Error('Your active character must be active to register sidekicks.');
}
} catch (error) {
this.container.logger.debug(error.message ?? 'Unexpected error cancelling transaction.', error);
if (interaction.deferred) {
return await interaction.editReply(error.message ?? 'Unexpected error cancelling transaction.');
} else {
return await interaction.update(error.message ?? 'Unexpected error cancelling transaction.');
}
}
}
}
export class SidekickRegisterCancelHandler extends InteractionHandler<{ interactionHandlerType: InteractionHandlerTypes.Button }> {
public async run(interaction: ButtonInteraction) {
try {
const player = await getPlayerByDiscordId(interaction.user.id);
if (isNullish(player)) {
throw new Error('Unable to retrieve player');
}
if (player.active_character && player.active_character.active) {
const deserialized = SidekickCustomIdStore.deserialize(interaction.customId).data;

// const registeredSidekick = await registerSidekickToCharacter(
// deserialized.playerId.toString(),
// deserialized.characterSlot,
// deserialized.name,
// SidekickTier[deserialized.cr],
// SidekickCreatureTypes[deserialized.creature],
// deserialized.purchased
// );

return interaction.editReply({ content: 'Sidekick registered', embeds: [], components: [] });
} else {
throw new Error('Your active character must be active to register sidekicks.');
}
} catch (error) {
this.container.logger.debug(error.message ?? 'Unexpected error cancelling transaction.', error);
if (interaction.deferred) {
return await interaction.editReply(error.message ?? 'Unexpected error cancelling transaction.');
} else {
return await interaction.update(error.message ?? 'Unexpected error cancelling transaction.');
}
}
}
}
8 replies
how to pass variables from one interaction into the next?
This is a really cool package can’t wait to try it. Going to migrate my sapphire bot to incorporate it
52 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
That was it thanks again
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
I’ve been swamped at work but will try this thanks
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
I updated to this but it still doesn’t allow you to provide the payload. I just skipped the task and use TimerManager.setTimeout to do it without
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
* declare module '@sapphire/plugin-scheduled-tasks' {
* interface ScheduledTasks {
* // A task named `Mute` which requires no payload:
* Mute: never;
*
* // A task named `Unmute` which requires a payload with a `userId` property:
* Unmute: {
* userId: string;
* };
*
* // A task named `Ban` which has a payload with an optional `moderatorId` property:
* LogAction: {
* moderatorId?: string;
* };
* }
* }
*
* declare module '@sapphire/plugin-scheduled-tasks' {
* interface ScheduledTasks {
* // A task named `Mute` which requires no payload:
* Mute: never;
*
* // A task named `Unmute` which requires a payload with a `userId` property:
* Unmute: {
* userId: string;
* };
*
* // A task named `Ban` which has a payload with an optional `moderatorId` property:
* LogAction: {
* moderatorId?: string;
* };
* }
* }
*
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
I see the change now though it's in the comments below and is done through module declaration
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
/**
* Creates a scheduled task.
*
* @param task - The task to be scheduled.
* @param payload - The payload for the task.
* @param options - The options for the task.
*/
create<T extends ScheduledTasksResolvable>(task: T, //
options?: ScheduledTasksTaskOptions | number): Promise<ScheduledTasksJob<T>>;
/**
* Creates a scheduled task.
*
* @param task - The task to be scheduled.
* @param payload - The payload for the task.
* @param options - The options for the task.
*/
create<T extends ScheduledTasksResolvable>(task: T, //
options?: ScheduledTasksTaskOptions | number): Promise<ScheduledTasksJob<T>>;
this looks like it only takes the options or a number (delay I assume).
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
ok thank you I'll try that
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
{
"name": "beholder",
"version": "8.3.0",
"description": "A bot used to manage and interact with the D&D 5e Discord Server Engrimoore.",
"author": "Engrimoore Code Weavers",
"license": "Apache-2.0",
"main": "dist/beholder.js",
"private": true,
"type": "commonjs",
"engines":{
"node": "18.18.2",
"npm": "10.2.1"
},
"dependencies": {
"@sapphire/bitfield": "^1.2.2",
"@sapphire/decorators": "^6.1.0",
"@sapphire/discord-utilities": "^3.3.0",
"@sapphire/discord.js-utilities": "^7.2.1",
"@sapphire/eslint-config": "^5.0.4",
"@sapphire/eslint-plugin-result": "^2.0.3",
"@sapphire/fetch": "^3.0.2",
"@sapphire/framework": "5.2.1",
"@sapphire/lexure": "^1.1.7",
"@sapphire/pieces": "^4.2.2",
"@sapphire/plugin-api": "^6.1.1",
"@sapphire/plugin-editable-commands": "^4.0.2",
"@sapphire/plugin-i18next": "^7.1.2",
"@sapphire/plugin-logger": "^4.0.2",
"@sapphire/plugin-pattern-commands": "^6.0.2",
"@sapphire/plugin-scheduled-tasks": "^10.0.1",
"@sapphire/plugin-subcommands": "^6.0.3",
"@sapphire/result": "^2.6.6",
"@sapphire/shapeshift": "^4.0.0",
"@sapphire/snowflake": "^3.5.3",
"@sapphire/stopwatch": "^1.5.2",
"@sapphire/time-utilities": "^1.7.12",
"@sapphire/type": "^2.4.4",
"@sapphire/utilities": "^3.16.2",
"@skyra/env-utilities": "^1.3.0",
"colorette": "^2.0.20",
"discord.js": "^14.15.2",
"dotenv-cra": "^3.0.3",
"reflect-metadata": "^0.2.2",
"ws": "^8.17.0"
},
"devDependencies": {
"@sapphire/prettier-config": "^2.0.0",
"@sapphire/ts-config": "^5.0.0",
"@types/node": "^20.11.5",
"@types/ws": "^8.5.10",
"npm-run-all": "^4.1.5",
"prettier": "^3.2.4",
"tsc-watch": "^6.0.4",
"typescript": "^5.3.3"
},
"scripts": {
"build": "tsc",
"watch": "tsc -w",
"start": "node dist/beholder.js",
"dev": "run-s build start",
"prod:test": "NODE_ENV=production node dist/beholder.js",
"watch:start": "tsc-watch --onSuccess \"node ./dist/beholder.js\"",
"format": "prettier --write \"src/**/*.ts\""
},
"prettier": "@sapphire/prettier-config"
}
{
"name": "beholder",
"version": "8.3.0",
"description": "A bot used to manage and interact with the D&D 5e Discord Server Engrimoore.",
"author": "Engrimoore Code Weavers",
"license": "Apache-2.0",
"main": "dist/beholder.js",
"private": true,
"type": "commonjs",
"engines":{
"node": "18.18.2",
"npm": "10.2.1"
},
"dependencies": {
"@sapphire/bitfield": "^1.2.2",
"@sapphire/decorators": "^6.1.0",
"@sapphire/discord-utilities": "^3.3.0",
"@sapphire/discord.js-utilities": "^7.2.1",
"@sapphire/eslint-config": "^5.0.4",
"@sapphire/eslint-plugin-result": "^2.0.3",
"@sapphire/fetch": "^3.0.2",
"@sapphire/framework": "5.2.1",
"@sapphire/lexure": "^1.1.7",
"@sapphire/pieces": "^4.2.2",
"@sapphire/plugin-api": "^6.1.1",
"@sapphire/plugin-editable-commands": "^4.0.2",
"@sapphire/plugin-i18next": "^7.1.2",
"@sapphire/plugin-logger": "^4.0.2",
"@sapphire/plugin-pattern-commands": "^6.0.2",
"@sapphire/plugin-scheduled-tasks": "^10.0.1",
"@sapphire/plugin-subcommands": "^6.0.3",
"@sapphire/result": "^2.6.6",
"@sapphire/shapeshift": "^4.0.0",
"@sapphire/snowflake": "^3.5.3",
"@sapphire/stopwatch": "^1.5.2",
"@sapphire/time-utilities": "^1.7.12",
"@sapphire/type": "^2.4.4",
"@sapphire/utilities": "^3.16.2",
"@skyra/env-utilities": "^1.3.0",
"colorette": "^2.0.20",
"discord.js": "^14.15.2",
"dotenv-cra": "^3.0.3",
"reflect-metadata": "^0.2.2",
"ws": "^8.17.0"
},
"devDependencies": {
"@sapphire/prettier-config": "^2.0.0",
"@sapphire/ts-config": "^5.0.0",
"@types/node": "^20.11.5",
"@types/ws": "^8.5.10",
"npm-run-all": "^4.1.5",
"prettier": "^3.2.4",
"tsc-watch": "^6.0.4",
"typescript": "^5.3.3"
},
"scripts": {
"build": "tsc",
"watch": "tsc -w",
"start": "node dist/beholder.js",
"dev": "run-s build start",
"prod:test": "NODE_ENV=production node dist/beholder.js",
"watch:start": "tsc-watch --onSuccess \"node ./dist/beholder.js\"",
"format": "prettier --write \"src/**/*.ts\""
},
"prettier": "@sapphire/prettier-config"
}
15 replies
SIASapphire - Imagine a framework
Created by WhacK on 7/22/2024 in #sapphire-support
manual task compiler error
// where the task is called
if (xpGain === 0) {
// TODO - fix manual task creation
const offset = this.container.prod ? Time.Minute * 30 : Time.Minute;
this.container.tasks.create('delete-message', { payload: message }, offset);
}
// where the task is called
if (xpGain === 0) {
// TODO - fix manual task creation
const offset = this.container.prod ? Time.Minute * 30 : Time.Minute;
this.container.tasks.create('delete-message', { payload: message }, offset);
}
import { ScheduledTask } from '@sapphire/plugin-scheduled-tasks';
import { ApplyOptions } from '@sapphire/decorators';
import { Message } from 'discord.js';
import { isNullishOrEmpty } from '@sapphire/utilities';

@ApplyOptions<ScheduledTask.Options>({
name: 'delete-message',
customJobOptions: {
removeOnComplete: true
}
})
export class DeleteMessageTask extends ScheduledTask {
protected async cleanupMessage(message: Message<boolean>) {
try {
if (message && message.deletable) {
const deleted = await message.delete().catch(() => []);
return isNullishOrEmpty(deleted) ? Promise.reject('Unable to delete message.') : Promise.resolve();
}
throw new Error('Message cannot be deleted.');
} catch (error) {
const message = error.message ?? 'Unknown error occurred cleaning up message.';
this.container.logger.debug(message, error);
return Promise.reject(message);
}
}

protected isMessage(payload: unknown): payload is Message<boolean> {
if (typeof payload !== 'object' || payload === null) {
return false;
}
const msg = payload as Message<boolean>;
return typeof msg.id === 'string' && typeof msg.content === 'string' && typeof msg.author === 'object';
}

public async run(payload: unknown) {
if (this.isMessage(payload)) return await this.cleanupMessage(payload);

return;
}
}
import { ScheduledTask } from '@sapphire/plugin-scheduled-tasks';
import { ApplyOptions } from '@sapphire/decorators';
import { Message } from 'discord.js';
import { isNullishOrEmpty } from '@sapphire/utilities';

@ApplyOptions<ScheduledTask.Options>({
name: 'delete-message',
customJobOptions: {
removeOnComplete: true
}
})
export class DeleteMessageTask extends ScheduledTask {
protected async cleanupMessage(message: Message<boolean>) {
try {
if (message && message.deletable) {
const deleted = await message.delete().catch(() => []);
return isNullishOrEmpty(deleted) ? Promise.reject('Unable to delete message.') : Promise.resolve();
}
throw new Error('Message cannot be deleted.');
} catch (error) {
const message = error.message ?? 'Unknown error occurred cleaning up message.';
this.container.logger.debug(message, error);
return Promise.reject(message);
}
}

protected isMessage(payload: unknown): payload is Message<boolean> {
if (typeof payload !== 'object' || payload === null) {
return false;
}
const msg = payload as Message<boolean>;
return typeof msg.id === 'string' && typeof msg.content === 'string' && typeof msg.author === 'object';
}

public async run(payload: unknown) {
if (this.isMessage(payload)) return await this.cleanupMessage(payload);

return;
}
}
15 replies
DIdiscord.js - Imagine ❄
Created by WhacK on 3/7/2024 in #djs-questions
reply to message with channel webhook
It also accepts a MessagePayload so I thought it might be possible but I'll have to go back to copying the prior content and appending with markdown
10 replies
DIdiscord.js - Imagine ❄
Created by WhacK on 3/7/2024 in #djs-questions
reply to message with channel webhook
No description
10 replies
DIdiscord.js - Imagine ❄
Created by WhacK on 3/7/2024 in #djs-questions
reply to message with channel webhook
[email protected] /Users/sr/Engrimoore/Beholder └── [email protected] -> % node -v v18.18.2
10 replies
SIASapphire - Imagine a framework
Created by ademondev on 2/14/2024 in #sapphire-support
How do interaction handlers pair up with commands
Sapphire uses the same instructions for slash command options as discordjs. This is the link in the sapphire docs https://discordjs.guide/slash-commands/parsing-options.html#command-options
7 replies
SIASapphire - Imagine a framework
Created by Slime on 2/13/2024 in #sapphire-support
Implement paginator , selection
I do something similar in my bot, I could not find a prebuilt class that handles that. Paginated Message would work but it’s not designed for that kind of functionality specifically so you’d have to override it. I use interaction handlers to do it in mine and it works really well. https://sapphirejs.dev/docs/Guide/interaction-handlers/what-are-they
7 replies
SIASapphire - Imagine a framework
Created by imvsc on 12/12/2023 in #discordjs-support
Editing an ephemeral reply from an interaction handler
Read about button interactions and their methods interaction.update in particular.
9 replies