mirror of
https://github.com/discordeno/discordeno.git
synced 2026-06-03 01:10:07 +00:00
Channel structure + fixes
This commit is contained in:
@@ -1,144 +1,39 @@
|
||||
import { eventHandlers } from "../bot.ts";
|
||||
import { cache } from "../cache.ts";
|
||||
import { channelOverwriteHasPermission } from "../helpers/channels/channel_overwrite_has_permission.ts";
|
||||
import { cloneChannel } from "../helpers/channels/clone_channel.ts";
|
||||
import { deleteChannel } from "../helpers/channels/delete_channel.ts";
|
||||
import { deleteChannelOverwrite } from "../helpers/channels/delete_channel_overwrite.ts";
|
||||
import { editChannel } from "../helpers/channels/edit_channel.ts";
|
||||
import { editChannelOverwrite } from "../helpers/channels/edit_channel_overwrite.ts";
|
||||
import { sendMessage } from "../helpers/messages/send_message.ts";
|
||||
import { disconnectMember } from "../helpers/mod.ts";
|
||||
import type { Channel } from "../types/channels/channel.ts";
|
||||
import { DiscordChannelTypes } from "../types/channels/channel_types.ts";
|
||||
import type { ModifyChannel } from "../types/channels/modify_channel.ts";
|
||||
import type { DiscordOverwrite, Overwrite } from "../types/channels/overwrite.ts";
|
||||
import type { CreateMessage } from "../types/messages/create_message.ts";
|
||||
import type { PermissionStrings } from "../types/permissions/permission_strings.ts";
|
||||
import { snowflakeToBigint } from "../util/bigint.ts";
|
||||
import { Collection } from "../util/collection.ts";
|
||||
import { createNewProp } from "../util/utils.ts";
|
||||
import { DiscordenoGuild } from "./guild.ts";
|
||||
import { DiscordenoMember } from "./member.ts";
|
||||
import { DiscordenoMessage } from "./message.ts";
|
||||
import { DiscordenoVoiceState } from "./voice_state.ts";
|
||||
import { Channel } from "../types/channels/channel.ts";
|
||||
import { Bot } from "../bot.ts";
|
||||
import { SnakeCasedPropertiesDeep } from "../types/util.ts";
|
||||
import { DiscordOverwrite } from "../types/channels/overwrite.ts";
|
||||
|
||||
const CHANNEL_SNOWFLAKES = ["id", "guildId", "lastMessageId", "ownerId", "applicationId", "parentId"];
|
||||
export function transformChannel(bot: Bot, payload: { channel: SnakeCasedPropertiesDeep<Channel> } & { guildId?: bigint }) {
|
||||
return {
|
||||
// UNTRANSFORMED STUFF HERE
|
||||
type: payload.channel.type,
|
||||
position: payload.channel.position,
|
||||
name: payload.channel.name,
|
||||
topic: payload.channel.topic,
|
||||
nsfw: payload.channel.nsfw,
|
||||
bitrate: payload.channel.bitrate,
|
||||
userLimit: payload.channel.user_limit,
|
||||
rateLimitPerUser: payload.channel.rate_limit_per_user,
|
||||
recipients: payload.channel.recipients,
|
||||
icon: payload.channel.icon,
|
||||
rtcRegion: payload.channel.rtc_region,
|
||||
videoQualityMode: payload.channel.video_quality_mode,
|
||||
guildId: payload.guildId || (payload.channel.guild_id ? bot.transformers.snowflake(payload.channel.guild_id) : 0n),
|
||||
lastPinTimestamp: payload.channel.last_pin_timestamp,
|
||||
permissionOverwrites: payload.channel.permission_overwrites ? payload.channel.permission_overwrites.map((o) => ({
|
||||
type: o.type,
|
||||
id: bot.transformers.snowflake(o.id),
|
||||
allow: bot.transformers.snowflake(o.allow),
|
||||
deny: bot.transformers.snowflake(o.deny),
|
||||
})) : [],
|
||||
|
||||
const baseChannel: Partial<DiscordenoChannel> = {
|
||||
toJSON() {
|
||||
return {
|
||||
id: this.id?.toString(),
|
||||
type: this.type,
|
||||
guildId: this.guildId?.toString(),
|
||||
position: this.position,
|
||||
permissionOverwrites: this.permissionOverwrites?.map((o) => ({
|
||||
...o,
|
||||
id: o.id.toString(),
|
||||
allow: o.allow.toString(),
|
||||
deny: o.deny.toString(),
|
||||
})),
|
||||
name: this.name,
|
||||
topic: this.topic,
|
||||
nsfw: this.nsfw,
|
||||
lastMessageId: this.lastMessageId?.toString(),
|
||||
bitrate: this.bitrate,
|
||||
userLimit: this.userLimit,
|
||||
rateLimitPerUser: this.rateLimitPerUser,
|
||||
recipients: this.recipients,
|
||||
icon: this.icon,
|
||||
ownerId: this.ownerId,
|
||||
applicationId: this.applicationId,
|
||||
parentId: this.parentId,
|
||||
lastPinTimestamp: this.lastPinTimestamp ? new Date(this.lastPinTimestamp).toISOString() : undefined,
|
||||
rtcRegion: this.rtcRegion,
|
||||
videoQualityMode: this.videoQualityMode,
|
||||
} as Channel;
|
||||
},
|
||||
get guild() {
|
||||
return cache.guilds.get(this.guildId!);
|
||||
},
|
||||
get messages() {
|
||||
return cache.messages.filter((m) => m.channelId === this.id!);
|
||||
},
|
||||
get mention() {
|
||||
return `<#${this.id!}>`;
|
||||
},
|
||||
get voiceStates() {
|
||||
return this.guild?.voiceStates.filter((voiceState) => voiceState.channelId === this.id!);
|
||||
},
|
||||
get connectedMembers() {
|
||||
const voiceStates = this.voiceStates;
|
||||
if (!voiceStates) return undefined;
|
||||
|
||||
return new Collection(voiceStates.map((vs) => [vs.userId, cache.members.get(vs.userId)]));
|
||||
},
|
||||
get isNewsChannel() {
|
||||
return this.type === DiscordChannelTypes.GuildNews;
|
||||
},
|
||||
get isGuildTextBasedChannel() {
|
||||
return [DiscordChannelTypes.GuildNews, DiscordChannelTypes.GuildText].includes(this.type!);
|
||||
},
|
||||
send(content) {
|
||||
return sendMessage(this.id!, content);
|
||||
},
|
||||
disconnect(memberId) {
|
||||
return disconnectMember(this.guildId!, memberId);
|
||||
},
|
||||
delete(reason) {
|
||||
return deleteChannel(this.id!, reason);
|
||||
},
|
||||
editOverwrite(id, options) {
|
||||
return editChannelOverwrite(this.guildId!, this.id!, id, options);
|
||||
},
|
||||
deleteOverwrite(id) {
|
||||
return deleteChannelOverwrite(this.guildId!, this.id!, id);
|
||||
},
|
||||
hasPermission(overwrites, permissions) {
|
||||
return channelOverwriteHasPermission(this.guildId!, this.id!, overwrites, permissions);
|
||||
},
|
||||
edit(options, reason) {
|
||||
return editChannel(this.id!, options, reason);
|
||||
},
|
||||
clone(reason) {
|
||||
return cloneChannel(this.id!, reason);
|
||||
},
|
||||
};
|
||||
|
||||
/** Create a structure object */
|
||||
// deno-lint-ignore require-await
|
||||
export async function createDiscordenoChannel(data: Channel, guildId?: bigint) {
|
||||
const { lastPinTimestamp, permissionOverwrites = [], ...rest } = data;
|
||||
|
||||
const requiredPropsSize = cache.requiredStructureProperties.channels.size;
|
||||
|
||||
const props: Record<string, PropertyDescriptor> = {};
|
||||
for (const key of Object.keys(rest) as (keyof typeof rest)[]) {
|
||||
eventHandlers.debug?.("loop", `Running forEach loop in createDiscordenoChannel function.`);
|
||||
// If empty then support all, otherwise we only allow the ones user added
|
||||
if (requiredPropsSize && !cache.requiredStructureProperties.channels.has(key)) continue;
|
||||
|
||||
props[key] = createNewProp(
|
||||
CHANNEL_SNOWFLAKES.includes(key) ? (rest[key] ? snowflakeToBigint(rest[key] as string) : undefined) : rest[key]
|
||||
);
|
||||
// TRANSFORMED STUFF BELOW
|
||||
id: bot.transformers.snowflake(payload.channel.id),
|
||||
lastMessageId: payload.channel.last_message_id ? bot.transformers.snowflake(payload.channel.last_message_id) : undefined,
|
||||
ownerId: payload.channel.owner_id ? bot.transformers.snowflake(payload.channel.owner_id) : undefined,
|
||||
applicationId: payload.channel.application_id ? bot.transformers.snowflake(payload.channel.application_id) : undefined,
|
||||
parentId: payload.channel.parent_id ? bot.transformers.snowflake(payload.channel.parent_id) : undefined,
|
||||
}
|
||||
|
||||
// Set the guildId seperately because sometimes guildId is not included
|
||||
if (!requiredPropsSize || cache.requiredStructureProperties.channels.has("guildId"))
|
||||
props.guildId = createNewProp(snowflakeToBigint(guildId?.toString() || data.guildId || ""));
|
||||
|
||||
if (!requiredPropsSize || cache.requiredStructureProperties.channels.has("lastPinTimestamp"))
|
||||
props.lastPinTimestamp = createNewProp(lastPinTimestamp ? Date.parse(lastPinTimestamp) : undefined);
|
||||
if (!requiredPropsSize || cache.requiredStructureProperties.channels.has("permissionOverwrites"))
|
||||
props.permissionOverwrites = createNewProp(
|
||||
permissionOverwrites.map((o) => ({
|
||||
...o,
|
||||
id: snowflakeToBigint(o.id),
|
||||
allow: snowflakeToBigint(o.allow),
|
||||
deny: snowflakeToBigint(o.deny),
|
||||
}))
|
||||
);
|
||||
|
||||
return Object.create(baseChannel, props) as DiscordenoChannel;
|
||||
}
|
||||
|
||||
export interface DiscordenoChannel
|
||||
@@ -173,64 +68,4 @@ export interface DiscordenoChannel
|
||||
applicationId?: bigint;
|
||||
/** Id of the parent category for a channel (each parent category can contain up to 50 channels) */
|
||||
parentId?: bigint;
|
||||
// GETTERS
|
||||
|
||||
/**
|
||||
* Gets the guild object for this channel.
|
||||
*
|
||||
* ⚠️ ADVANCED: If you use the custom cache, these will not work for you. Getters can not be async and custom cache requires async.
|
||||
*/
|
||||
guild?: DiscordenoGuild;
|
||||
/**
|
||||
* Gets the messages from cache that were sent in this channel
|
||||
*
|
||||
* ⚠️ ADVANCED: If you use the custom cache, these will not work for you. Getters can not be async and custom cache requires async.
|
||||
*/
|
||||
messages: Collection<bigint, DiscordenoMessage>;
|
||||
/** The mention of the channel */
|
||||
mention: string;
|
||||
/**
|
||||
* Gets the voice states for this channel
|
||||
*
|
||||
* ⚠️ ADVANCED: If you use the custom cache, these will not work for you. Getters can not be async and custom cache requires async.
|
||||
*/
|
||||
voiceStates?: Collection<bigint, DiscordenoVoiceState>;
|
||||
/**
|
||||
* Gets the connected members for this channel undefined if member is not cached
|
||||
*
|
||||
* ⚠️ ADVANCED: If you use the custom cache, these will not work for you. Getters can not be async and custom cache requires async.
|
||||
*/
|
||||
connectedMembers?: Collection<bigint, DiscordenoMember | undefined>;
|
||||
/** Whether the channel is a news channel. */
|
||||
isNewsChannel: boolean;
|
||||
/** Whether the channel is a news or text channel in a guild. */
|
||||
isGuildTextBasedChannel: boolean;
|
||||
|
||||
// METHODS
|
||||
|
||||
/** Send a message to the channel. Requires SEND_MESSAGES permission. */
|
||||
send(content: string | CreateMessage): ReturnType<typeof sendMessage>;
|
||||
/** Disconnect a member from a voice channel. Requires MOVE_MEMBERS permission. */
|
||||
disconnect(memberId: bigint): ReturnType<typeof disconnectMember>;
|
||||
/** Delete the channel */
|
||||
delete(reason?: string): ReturnType<typeof deleteChannel>;
|
||||
/** Edit a channel Overwrite */
|
||||
editOverwrite(overwriteId: bigint, options: Omit<Overwrite, "id">): ReturnType<typeof editChannelOverwrite>;
|
||||
/** Delete a channel Overwrite */
|
||||
deleteOverwrite(overwriteId: bigint): ReturnType<typeof deleteChannelOverwrite>;
|
||||
/** Checks if a channel overwrite for a user id or a role id has permission in this channel */
|
||||
hasPermission(
|
||||
overwrites: (Omit<DiscordOverwrite, "id" | "allow" | "deny"> & {
|
||||
id: bigint;
|
||||
allow: bigint;
|
||||
deny: bigint;
|
||||
})[],
|
||||
permissions: PermissionStrings[]
|
||||
): ReturnType<typeof channelOverwriteHasPermission>;
|
||||
/** Edit the channel */
|
||||
edit(options: ModifyChannel, reason?: string): ReturnType<typeof editChannel>;
|
||||
/** Create a new channel with the same properties */
|
||||
clone(reason?: string): ReturnType<typeof cloneChannel>;
|
||||
/** Returns the Channel object json value */
|
||||
toJSON(): Channel;
|
||||
}
|
||||
|
||||
@@ -1,16 +1,17 @@
|
||||
import { Bot } from "../bot.ts";
|
||||
import { Message } from "../types/messages/message.ts";
|
||||
import { CHANNEL_MENTION_REGEX } from "../util/constants.ts";
|
||||
import { SnakeCasedPropertiesDeep } from "../types/util.ts";
|
||||
|
||||
export function transformMessage(bot: Bot, data: Message) {
|
||||
export function transformMessage(bot: Bot, data: SnakeCasedPropertiesDeep<Message>) {
|
||||
return {
|
||||
// UNTRANSFORMED STUFF HERE
|
||||
content: data.content || "",
|
||||
isBot: data.author.bot || false,
|
||||
tag: `${data.author.username}#${data.author.discriminator.toString().padStart(4, "0")}`,
|
||||
timestamp: Date.parse(data.timestamp),
|
||||
editedTimestamp: data.editedTimestamp ? Date.parse(data.editedTimestamp) : undefined,
|
||||
bitfield: (data.tts ? 1n : 0n) | (data.mentionEveryone ? 2n : 0n) | (data.pinned ? 4n : 0n),
|
||||
editedTimestamp: data.edited_timestamp ? Date.parse(data.edited_timestamp) : undefined,
|
||||
bitfield: (data.tts ? 1n : 0n) | (data.mention_everyone ? 2n : 0n) | (data.pinned ? 4n : 0n),
|
||||
attachments: data.attachments,
|
||||
embeds: data.embeds,
|
||||
reactions: data.reactions,
|
||||
@@ -21,33 +22,33 @@ export function transformMessage(bot: Bot, data: Message) {
|
||||
interaction: data.interaction,
|
||||
thread: data.thread,
|
||||
components: data.components,
|
||||
stickerItems: data.stickerItems,
|
||||
stickerItems: data.sticker_items,
|
||||
|
||||
// TRANSFORMED STUFF BELOW
|
||||
id: bot.transformers.snowflake(data.id),
|
||||
guildId: data.guildId ? bot.transformers.snowflake(data.guildId) : undefined,
|
||||
channelId: bot.transformers.snowflake(data.channelId),
|
||||
webhookId: data.webhookId ? bot.transformers.snowflake(data.webhookId) : undefined,
|
||||
guildId: data.guild_id ? bot.transformers.snowflake(data.guild_id) : undefined,
|
||||
channelId: bot.transformers.snowflake(data.channel_id),
|
||||
webhookId: data.webhook_id ? bot.transformers.snowflake(data.webhook_id) : undefined,
|
||||
authorId: bot.transformers.snowflake(data.author.id),
|
||||
applicationId: data.applicationId ? bot.transformers.snowflake(data.applicationId) : undefined,
|
||||
messageReference: data.messageReference
|
||||
applicationId: data.application_id ? bot.transformers.snowflake(data.application_id) : undefined,
|
||||
messageReference: data.message_reference
|
||||
? {
|
||||
messageId: data.messageReference.messageId
|
||||
? bot.transformers.snowflake(data.messageReference.messageId)
|
||||
messageId: data.message_reference.message_id
|
||||
? bot.transformers.snowflake(data.message_reference.message_id)
|
||||
: undefined,
|
||||
channelId: data.messageReference.channelId
|
||||
? bot.transformers.snowflake(data.messageReference.channelId)
|
||||
channelId: data.message_reference.channel_id
|
||||
? bot.transformers.snowflake(data.message_reference.channel_id)
|
||||
: undefined,
|
||||
guildId: data.messageReference.guildId
|
||||
? bot.transformers.snowflake(data.messageReference.guildId)
|
||||
guildId: data.message_reference.guild_id
|
||||
? bot.transformers.snowflake(data.message_reference.guild_id)
|
||||
: undefined,
|
||||
}
|
||||
: undefined,
|
||||
mentionedUserIds: data.mentions.map((m) => bot.transformers.snowflake(m.id)),
|
||||
mentionedRoleIds: data.mentionRoles.map((id) => bot.transformers.snowflake(id)),
|
||||
mentionedUserIds: data.mentions ? data.mentions.map((m) => bot.transformers.snowflake(m.id)) : [],
|
||||
mentionedRoleIds: data.mention_roles ? data.mention_roles.map((id) => bot.transformers.snowflake(id)) : [],
|
||||
mentionedChannelIds: [
|
||||
// Keep any ids tht discord sends
|
||||
...data.mentionChannels.map((m) => bot.transformers.snowflake(m.id)),
|
||||
...(data.mention_channels ?? []).map((m) => bot.transformers.snowflake(m.id)),
|
||||
// Add any other ids that can be validated in a channel mention format
|
||||
...(data.content?.match(CHANNEL_MENTION_REGEX) || []).map((text) =>
|
||||
// converts the <#123> into 123
|
||||
|
||||
@@ -1,12 +1,13 @@
|
||||
import { Bot } from "../bot.ts";
|
||||
import { Role } from "../types/mod.ts";
|
||||
import { SnakeCasedPropertiesDeep } from "../types/util.ts";
|
||||
|
||||
export function transformRole(
|
||||
bot: Bot,
|
||||
payload: { role: Role } & {
|
||||
payload: { role: SnakeCasedPropertiesDeep<Role> } & {
|
||||
guildId: bigint;
|
||||
}
|
||||
) {
|
||||
): DiscordenoRole {
|
||||
return {
|
||||
// UNTRANSFORMED STUFF HERE
|
||||
name: payload.role.name,
|
||||
@@ -17,15 +18,15 @@ export function transformRole(
|
||||
(payload.role.hoist ? 1n : 0n) |
|
||||
(payload.role.managed ? 2n : 0n) |
|
||||
(payload.role.mentionable ? 4n : 0n) |
|
||||
(payload.role.tags?.premiumSubscriber ? 8n : 0n),
|
||||
(payload.role.tags?.premium_subscriber ? 8n : 0n),
|
||||
|
||||
// TRANSFORMED STUFF BELOW
|
||||
id: bot.transformers.snowflake(payload.role.id),
|
||||
botId: payload.role.tags?.botId ? bot.transformers.snowflake(payload.role.tags.botId) : undefined,
|
||||
integrationId: payload.role.tags?.integrationId
|
||||
? bot.transformers.snowflake(payload.role.tags.integrationId)
|
||||
botId: payload.role.tags?.bot_id ? bot.transformers.snowflake(payload.role.tags.bot_id) : undefined,
|
||||
integrationId: payload.role.tags?.integration_id
|
||||
? bot.transformers.snowflake(payload.role.tags.integration_id)
|
||||
: undefined,
|
||||
permissions: payload.role.permissions ? bot.transformers.snowflake(payload.role.permissions) : undefined,
|
||||
permissions: bot.transformers.snowflake(payload.role.permissions),
|
||||
};
|
||||
}
|
||||
|
||||
@@ -37,7 +38,7 @@ export interface DiscordenoRole extends Omit<Role, "tags" | "id" | "permissions"
|
||||
/** If this role is the nitro boost role. */
|
||||
isNitroBoostRole: boolean;
|
||||
/** The integration id that is associated with this role */
|
||||
integrationId: bigint;
|
||||
integrationId?: bigint;
|
||||
/** The roles guildId */
|
||||
guildId: bigint;
|
||||
/** Permission bit set */
|
||||
|
||||
Reference in New Issue
Block a user