mirror of
https://github.com/discordjs/discord.js.git
synced 2026-03-09 16:13:31 +01:00
feat: message forwards (#10733)
* feat: message forwards * fix: spelling * feat: add guildId option for forward * refactor: type * refactor: do not use ID suffix for resolvables * Update TextBasedChannel.js --------- Co-authored-by: Jiralite <33201955+Jiralite@users.noreply.github.com>
This commit is contained in:
@@ -9,6 +9,7 @@ const {
|
||||
MessageType,
|
||||
MessageFlags,
|
||||
PermissionFlagsBits,
|
||||
MessageReferenceType,
|
||||
} = require('discord-api-types/v10');
|
||||
const Attachment = require('./Attachment');
|
||||
const Base = require('./Base');
|
||||
@@ -704,7 +705,11 @@ class Message extends Base {
|
||||
* @readonly
|
||||
*/
|
||||
get editable() {
|
||||
const precheck = Boolean(this.author.id === this.client.user.id && (!this.guild || this.channel?.viewable));
|
||||
const precheck = Boolean(
|
||||
this.author.id === this.client.user.id &&
|
||||
(!this.guild || this.channel?.viewable) &&
|
||||
this.reference?.type !== MessageReferenceType.Forward,
|
||||
);
|
||||
|
||||
// Regardless of permissions thread messages cannot be edited if
|
||||
// the thread is archived or the thread is locked and the bot does not have permission to manage threads.
|
||||
@@ -956,6 +961,24 @@ class Message extends Base {
|
||||
return this.channel.send(data);
|
||||
}
|
||||
|
||||
/**
|
||||
* Forwards this message
|
||||
*
|
||||
* @param {TextBasedChannelResolvable} channel The channel to forward this message to.
|
||||
* @returns {Promise<Message>}
|
||||
*/
|
||||
forward(channel) {
|
||||
const resolvedChannel = this.client.channels.resolve(channel);
|
||||
if (!resolvedChannel) throw new DiscordjsError(ErrorCodes.InvalidType, 'channel', 'TextBasedChannelResolvable');
|
||||
return resolvedChannel.send({
|
||||
forward: {
|
||||
message: this.id,
|
||||
channel: this.channelId,
|
||||
guild: this.guildId,
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Options for starting a thread on a message.
|
||||
* @typedef {Object} StartThreadOptions
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
const { Buffer } = require('node:buffer');
|
||||
const { lazy, isJSONEncodable } = require('@discordjs/util');
|
||||
const { DiscordSnowflake } = require('@sapphire/snowflake');
|
||||
const { MessageFlags } = require('discord-api-types/v10');
|
||||
const { MessageFlags, MessageReferenceType } = require('discord-api-types/v10');
|
||||
const ActionRowBuilder = require('./ActionRowBuilder');
|
||||
const { DiscordjsError, DiscordjsRangeError, ErrorCodes } = require('../errors');
|
||||
const { resolveFile } = require('../util/DataResolver');
|
||||
@@ -199,6 +199,22 @@ class MessagePayload {
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof this.options.forward === 'object') {
|
||||
const reference = this.options.forward.message;
|
||||
const channel_id = reference.channelId ?? this.target.client.channels.resolveId(this.options.forward.channel);
|
||||
const guild_id = reference.guildId ?? this.target.client.guilds.resolveId(this.options.forward.guild);
|
||||
const message_id = this.target.messages.resolveId(reference);
|
||||
if (message_id) {
|
||||
if (!channel_id) throw new DiscordjsError(ErrorCodes.InvalidType, 'channelId', 'TextBasedChannelResolvable');
|
||||
message_reference = {
|
||||
type: MessageReferenceType.Forward,
|
||||
message_id,
|
||||
channel_id,
|
||||
guild_id: guild_id ?? undefined,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
const attachments = this.options.files?.map((file, index) => ({
|
||||
id: index.toString(),
|
||||
description: file.description,
|
||||
|
||||
@@ -110,10 +110,18 @@ class TextBasedChannel {
|
||||
* <info>Only `MessageFlags.SuppressEmbeds` and `MessageFlags.SuppressNotifications` can be set.</info>
|
||||
*/
|
||||
|
||||
/**
|
||||
* @typedef {Object} ForwardOptions
|
||||
* @property {MessageResolvable} message The originating message
|
||||
* @property {TextBasedChannelResolvable} [channel] The channel of the originating message
|
||||
* @property {GuildResolvable} [guild] The guild of the originating message
|
||||
*/
|
||||
|
||||
/**
|
||||
* The options for sending a message.
|
||||
* @typedef {BaseMessageCreateOptions} MessageCreateOptions
|
||||
* @property {ReplyOptions} [reply] The options for replying to a message
|
||||
* @property {ForwardOptions} [forward] The options for forwarding a message
|
||||
*/
|
||||
|
||||
/**
|
||||
|
||||
21
packages/discord.js/typings/index.d.ts
vendored
21
packages/discord.js/typings/index.d.ts
vendored
@@ -2310,6 +2310,7 @@ export class Message<InGuild extends boolean = boolean> extends Base {
|
||||
public reply(
|
||||
options: string | MessagePayload | MessageReplyOptions,
|
||||
): Promise<OmitPartialGroupDMChannel<Message<InGuild>>>;
|
||||
public forward(channel: Exclude<TextBasedChannelResolvable, PartialGroupDMChannel>): Promise<Message>;
|
||||
public resolveComponent(customId: string): MessageActionRowComponent | null;
|
||||
public startThread(options: StartThreadOptions): Promise<PublicThreadChannel<false>>;
|
||||
public suppressEmbeds(suppress?: boolean): Promise<OmitPartialGroupDMChannel<Message<InGuild>>>;
|
||||
@@ -6759,6 +6760,7 @@ export interface MessageCreateOptions extends BaseMessageOptionsWithPoll {
|
||||
nonce?: string | number;
|
||||
enforceNonce?: boolean;
|
||||
reply?: ReplyOptions;
|
||||
forward?: ForwardOptions;
|
||||
stickers?: readonly StickerResolvable[];
|
||||
flags?:
|
||||
| BitFieldResolvable<
|
||||
@@ -7011,7 +7013,21 @@ export interface ReplyOptions {
|
||||
failIfNotExists?: boolean;
|
||||
}
|
||||
|
||||
export interface MessageReplyOptions extends Omit<MessageCreateOptions, 'reply'> {
|
||||
export interface BaseForwardOptions {
|
||||
message: MessageResolvable;
|
||||
channel?: Exclude<TextBasedChannelResolvable, PartialGroupDMChannel>;
|
||||
guild?: GuildResolvable;
|
||||
}
|
||||
|
||||
export type ForwardOptionsWithMandatoryChannel = BaseForwardOptions & Required<Pick<BaseForwardOptions, 'channel'>>;
|
||||
|
||||
export interface ForwardOptionsWithOptionalChannel extends BaseForwardOptions {
|
||||
message: Exclude<MessageResolvable, Snowflake>;
|
||||
}
|
||||
|
||||
export type ForwardOptions = ForwardOptionsWithMandatoryChannel | ForwardOptionsWithOptionalChannel;
|
||||
|
||||
export interface MessageReplyOptions extends Omit<MessageCreateOptions, 'reply' | 'forward'> {
|
||||
failIfNotExists?: boolean;
|
||||
}
|
||||
|
||||
@@ -7290,7 +7306,8 @@ export interface WebhookFetchMessageOptions {
|
||||
threadId?: Snowflake;
|
||||
}
|
||||
|
||||
export interface WebhookMessageCreateOptions extends Omit<MessageCreateOptions, 'nonce' | 'reply' | 'stickers'> {
|
||||
export interface WebhookMessageCreateOptions
|
||||
extends Omit<MessageCreateOptions, 'nonce' | 'reply' | 'stickers' | 'forward'> {
|
||||
username?: string;
|
||||
avatarURL?: string;
|
||||
threadId?: Snowflake;
|
||||
|
||||
Reference in New Issue
Block a user