Merge pull request #769 from itohatweb/fix-types

types: add missing types
This commit is contained in:
Skillz4Killz
2021-04-08 09:52:31 -04:00
committed by GitHub
21 changed files with 235 additions and 48 deletions

View File

@@ -13,17 +13,30 @@ import { getInvites } from "../helpers/invites/get_invites.ts";
import { banMember } from "../helpers/members/ban_member.ts";
import { unbanMember } from "../helpers/members/unban_member.ts";
import { GetGuildAuditLog } from "../types/audit_log/get_guild_audit_log.ts";
import { Emoji } from "../types/emojis/emoji.ts";
import { CreateGuildBan } from "../types/guilds/create_guild_ban.ts";
import { DiscordGuild, Guild } from "../types/guilds/guild.ts";
import { DiscordGuildFeatures } from "../types/guilds/guild_features.ts";
import { GuildMember } from "../types/guilds/guild_member.ts";
import {
DiscordGuildMember,
GuildMember,
} from "../types/guilds/guild_member.ts";
import { ModifyGuild } from "../types/guilds/modify_guild.ts";
import { DiscordImageFormat } from "../types/misc/image_format.ts";
import { DiscordImageSize } from "../types/misc/image_size.ts";
import { PresenceUpdate } from "../types/misc/presence_update.ts";
import { DiscordUser } from "../types/users/user.ts";
import { VoiceState } from "../types/voice/voice_state.ts";
import { Collection } from "../util/collection.ts";
import { createNewProp, snakeKeysToCamelCase } from "../util/utils.ts";
import { RoleStruct, structures } from "./mod.ts";
import {
camelKeysToSnakeCase,
createNewProp,
snakeKeysToCamelCase,
} from "../util/utils.ts";
import { ChannelStruct } from "./channel.ts";
import { MemberStruct } from "./member.ts";
import { structures } from "./mod.ts";
import { RoleStruct } from "./role.ts";
export const initialMemberLoadQueue = new Map<string, GuildMember[]>();
@@ -118,7 +131,9 @@ export async function createGuildStruct(
} = snakeKeysToCamelCase(data) as Guild;
const roles = await Promise.all(
data.roles.map((role) => structures.createRoleStruct(role)),
data.roles.map((role) =>
structures.createRoleStruct({ role, guild_id: rest.id })
),
);
await Promise.all(channels.map(async (channel) => {
@@ -164,7 +179,9 @@ export async function createGuildStruct(
await Promise.allSettled(
members.map(async (member) => {
const memberStruct = await structures.createMemberStruct(
member,
camelKeysToSnakeCase(member) as Omit<DiscordGuildMember, "user"> & {
user: DiscordUser;
},
guild.id,
);
@@ -179,14 +196,25 @@ export async function createGuildStruct(
export interface GuildStruct extends
Omit<
Guild,
"roles" | "presences" | "voiceStates" | "members" | "channels"
| "roles"
| "presences"
| "voiceStates"
| "members"
| "channels"
| "memberCount"
| "owner"
| "emojis"
> {
/** Total number of members in this guild */
memberCount?: number;
/** The roles in the guild */
roles: Collection<string, RoleStruct>;
/** The presences of all the users in the guild. */
presences: Collection<string, PresenceUpdate>;
/** The Voice State data for each user in a voice channel in this server. */
voiceStates: Collection<string, CleanVoiceState>;
voiceStates: Collection<string, VoiceState>;
/** Custom guild emojis */
emojis: Collection<string, Emoji>;
// GETTERS
/** Members in this guild. */
@@ -204,9 +232,12 @@ export interface GuildStruct extends
/** The bot member in this guild if cached */
bot?: MemberStruct;
/** The bot guild member in this guild if cached */
botMember?: GuildMember;
botMember?: Omit<GuildMember, "joinedAt" | "premiumSince"> & {
joinedAt: number;
premiumSince?: number;
};
/** The bots voice state if there is one in this guild */
botVoice?: CleanVoiceState;
botVoice?: VoiceState;
/** The owner member of this guild */
owner?: MemberStruct;
/** Whether or not this guild is partnered */

View File

@@ -6,13 +6,13 @@ import { kickMember } from "../helpers/members/kick_member.ts";
import { sendDirectMessage } from "../helpers/members/send_direct_message.ts";
import { addRole } from "../helpers/roles/add_role.ts";
import { removeRole } from "../helpers/roles/remove_role.ts";
import { CreateMessage } from "../types/channels/create_message.ts";
import { CreateGuildBan } from "../types/guilds/create_guild_ban.ts";
import {
DiscordGuildMember,
GuildMember,
} from "../types/guilds/guild_member.ts";
import { ModifyGuildMember } from "../types/guilds/modify_guild_member.ts";
import { CreateMessage } from "../types/messages/create_message.ts";
import { DiscordImageFormat } from "../types/misc/image_format.ts";
import { DiscordImageSize } from "../types/misc/image_size.ts";
import { DiscordUser, User } from "../types/users/user.ts";
@@ -151,7 +151,14 @@ export interface MemberStruct extends GuildMember, User {
/** Get the nickname or the username if no nickname */
name(guildID: string): string;
/** Get the guild member object for the specified guild */
guildMember(guildID: string): GuildMember | undefined;
guildMember(
guildID: string,
):
| Omit<GuildMember, "joinedAt" | "premiumSince"> & {
joinedAt: number;
premiumSince?: number;
}
| undefined;
/** Send a direct message to the user is possible */
sendDM(
content: string | CreateMessage,

View File

@@ -9,10 +9,18 @@ import { removeAllReactions } from "../helpers/messages/remove_all_reactions.ts"
import { removeReaction } from "../helpers/messages/remove_reaction.ts";
import { removeReactionEmoji } from "../helpers/messages/remove_reaction_emoji.ts";
import { sendMessage } from "../helpers/messages/send_message.ts";
import { DiscordenoCreateMessage } from "../types/discordeno/create_message.ts";
import { GuildMember } from "../types/guilds/guild_member.ts";
import { EditMessage } from "../types/messages/edit_message.ts";
import { DiscordMessage, Message } from "../types/messages/message.ts";
import { CHANNEL_MENTION_REGEX } from "../util/constants.ts";
import { createNewProp } from "../util/utils.ts";
import { createNewProp, snakeKeysToCamelCase } from "../util/utils.ts";
import { ChannelStruct } from "./channel.ts";
import { GuildStruct } from "./guild.ts";
import { MemberStruct } from "./member.ts";
import { RoleStruct } from "./role.ts";
const baseMessage: Partial<Message> = {
const baseMessage: Partial<MessageStruct> = {
get channel() {
if (this.guildId) return cache.channels.get(this.channelId!);
return cache.channels.get(this.author?.id!);
@@ -34,13 +42,13 @@ const baseMessage: Partial<Message> = {
"@me"}/${this.channelId}/${this.id}`;
},
get mentionedRoles() {
return this.mentionRoleIds?.map((id) => this.guild?.roles.get(id)) || [];
return this.mentionedRoleIds?.map((id) => this.guild?.roles.get(id)) || [];
},
get mentionedChannels() {
return this.mentionChannelIds?.map((id) => cache.channels.get(id)) || [];
return this.mentionedChannelIds?.map((id) => cache.channels.get(id)) || [];
},
get mentionedMembers() {
return this.mentions?.map((id) => cache.members.get(id)) || [];
return this.mentionedUserIds?.map((id) => cache.members.get(id)) || [];
},
// METHODS
@@ -69,9 +77,10 @@ const baseMessage: Partial<Message> = {
}
: {
...content,
mentions: { ...(content.mentions || {}), repliedUser: true },
mentions: { ...(content.allowedMentions || {}), repliedUser: true },
replyMessageId: this.id,
failReplyIfNotExists: content.failReplyIfNotExists === true,
failReplyIfNotExists:
content.messageReference?.failIfNotExists === true,
};
if (this.guildId) return sendMessage(this.channelId!, contentWithMention);
@@ -108,58 +117,126 @@ const baseMessage: Partial<Message> = {
},
};
export async function createMessageStruct(data: MessageCreateOptions) {
export async function createMessageStruct(data: DiscordMessage) {
const {
guild_id: guildId = "",
channel_id: channelId,
mentions_everyone: mentionsEveryone,
mention_channels: mentionChannelIds = [],
mention_roles: mentionRoleIds,
webhook_id: webhookId,
message_reference: messageReference,
guildId = "",
channelId,
mentionChannels = [],
mentions,
mentionRoles,
edited_timestamp: editedTimestamp,
referenced_message: referencedMessageId,
member,
...rest
} = data;
} = snakeKeysToCamelCase(data) as Message;
const restProps: Record<string, ReturnType<typeof createNewProp>> = {};
const props: Record<string, ReturnType<typeof createNewProp>> = {};
for (const key of Object.keys(rest)) {
// @ts-ignore index signature
restProps[key] = createNewProp(rest[key]);
props[key] = createNewProp(rest[key]);
}
// Discord doesnt give guild id for getMessage() so this will fill it in
const guildIdFinal = guildId ||
(await cacheHandlers.get("channels", channelId))?.guildId || "";
const message = Object.create(baseMessage, {
...restProps,
const message: MessageStruct = Object.create(baseMessage, {
...props,
/** The message id of the original message if this message was sent as a reply. If null, the original message was deleted. */
referencedMessageId: createNewProp(referencedMessageId),
channelId: createNewProp(channelId),
guildId: createNewProp(guildId || guildIdFinal),
mentions: createNewProp(data.mentions.map((m) => m.id)),
mentionsEveryone: createNewProp(mentionsEveryone),
mentionRoleIds: createNewProp(mentionRoleIds),
mentionChannelIds: createNewProp(
guildId: createNewProp(guildIdFinal),
mentionedUserIds: createNewProp(mentions.map((m) => m.id)),
mentionedRoleIds: createNewProp(mentionRoles),
mentionedChannelIds: createNewProp(
[
// Keep any ids that discord sends
...mentionChannelIds,
...mentionChannels.map((m) => m.id),
// Add any other ids that can be validated in a channel mention format
...(rest.content.match(CHANNEL_MENTION_REGEX) || []).map((text) =>
// converts the <#123> into 123
text.substring(2, text.length - 1)
),
].map((m) => m.id),
],
),
webhookId: createNewProp(webhookId),
messageReference: createNewProp(messageReference),
timestamp: createNewProp(Date.parse(data.timestamp)),
editedTimestamp: createNewProp(
editedTimestamp ? Date.parse(editedTimestamp) : undefined,
),
});
return message as Message;
return message;
}
export interface MessageStruct extends Message {
// For better user experience
/** Ids of users specifically mentioned in the message */
mentionedUserIds: string[];
/** Ids of roles specifically mentioned in this message */
mentionedRoleIds: string[];
/** Channels specifically mentioned in this message */
mentionedChannelIds?: string[];
// GETTERS
/** The channel where this message was sent. Can be undefined if uncached. */
channel?: ChannelStruct;
/** The guild of this message. Can be undefined if not in cache or in DM */
guild?: GuildStruct;
/** The member for the user who sent the message. Can be undefined if not in cache or in dm. */
member?: MemberStruct;
/** The guild member details for this guild and member. Can be undefined if not in cache or in dm. */
guildMember?: Omit<GuildMember, "joinedAt" | "premiumSince"> & {
joinedAt: number;
premiumSince?: number;
};
/** The url link to this message */
link: string;
/** The role objects for all the roles that were mentioned in this message */
mentionedRoles: (RoleStruct | undefined)[];
/** The channel objects for all the channels that were mentioned in this message. */
mentionedChannels: (ChannelStruct | undefined)[];
/** The member objects for all the members that were mentioned in this message. */
mentionedMembers: (MemberStruct | undefined)[];
// METHODS
/** Delete the message */
delete(
reason?: string,
delayMilliseconds?: number,
): ReturnType<typeof deleteMessage>;
/** Edit the message */
edit(content: string | EditMessage): ReturnType<typeof editMessage>;
/** Pins the message in the channel */
pin(): ReturnType<typeof pinMessage>;
/** Add a reaction to the message */
addReaction(reaction: string): ReturnType<typeof addReaction>;
/** Add multiple reactions to the message without or without order. */
addReactions(
reactions: string[],
ordered?: boolean,
): ReturnType<typeof addReactions>;
/** Send a inline reply to this message */
reply(
content: string | DiscordenoCreateMessage,
): ReturnType<typeof sendMessage>;
/** Send a message to this channel where this message is */
send(
content: string | DiscordenoCreateMessage,
): ReturnType<typeof sendMessage>;
/** Send a message to this channel and then delete it after a bit. By default it will delete after 10 seconds with no reason provided. */
alert(
content: string | DiscordenoCreateMessage,
timeout?: number,
reason?: string,
): Promise<void>;
/** Send a inline reply to this message but then delete it after a bit. By default it will delete after 10 seconds with no reason provided. */
alertReply(
content: string | DiscordenoCreateMessage,
timeout?: number,
reason?: string,
): Promise<unknown>;
/** Remove all reactions */
removeAllReactions(): ReturnType<typeof removeAllReactions>;
/** Remove all reactions */
removeReactionEmoji(reaction: string): ReturnType<typeof removeReactionEmoji>;
/** Remove all reactions */
removeReaction(reaction: string): ReturnType<typeof removeReaction>;
}

View File

@@ -0,0 +1,7 @@
import { CreateGlobalApplicationCommand } from "../interactions/create_global_application_command.ts";
export interface DiscordenoCreateApplicationCommand
extends CreateGlobalApplicationCommand {
/** Id of the guild to create a guild only application command */
guildId: string;
}

View File

@@ -0,0 +1,6 @@
import { EditWebhookMessage } from "../webhooks/edit_webhook_message.ts";
export interface DiscordenoEditWebhookMessage extends EditWebhookMessage {
/** Id of the message you want to edit */
messageId: string;
}

View File

View File

@@ -0,0 +1,7 @@
import { Guild } from "../guilds/guild.ts";
export interface GuildUpdateChange {
key: keyof Guild;
oldValue?: unknown;
value?: unknown;
}

View File

@@ -0,0 +1,6 @@
import { InteractionResponse } from "../interactions/interaction_response.ts";
export interface DiscordenoInteractionResponse extends InteractionResponse {
/** Set to true if the response should be private */
private?: boolean;
}

View File

@@ -0,0 +1,12 @@
import { SnakeCaseProps } from "../util.ts";
import { Integration } from "./integration.ts";
export interface IntegrationCreateUpdate extends Integration {
/** Id of the guild */
guildId: string;
}
/** https://github.com/discord/discord-api-docs/blob/master/docs/topics/Gateway.md#integration-create-event-additional-fields */
export type DiscordIntegrationCreateUpdate = SnakeCaseProps<
IntegrationCreateUpdate
>;

View File

@@ -0,0 +1,13 @@
import { SnakeCaseProps } from "../util.ts";
export interface IntegrationDelete {
/** Integration id */
id: string;
/** Id of the guild */
guildId: string;
/** Id of the bot/OAuth2 application for this discord integration */
applicationId?: string;
}
/** https://github.com/discord/discord-api-docs/blob/master/docs/topics/Gateway.md#integration-delete-event-fields */
export type DiscordIntegrationDelete = SnakeCaseProps<IntegrationDelete>;

View File

@@ -1,3 +1,4 @@
import { GuildMember } from "../guilds/guild_member.ts";
import { User } from "../users/user.ts";
import { SnakeCaseProps } from "../util.ts";
import { InteractionApplicationCommandCallbackData } from "./application_command_callback_data.ts";

View File

@@ -5,11 +5,11 @@ export interface AllowedMentions {
/** An array of allowed mention types to parse from the content. */
parse: DiscordAllowedMentionsTypes[];
/** Array of role_ids to mention (Max size of 100) */
roles: string[];
roles?: string[];
/** Array of user_ids to mention (Max size of 100) */
users: string[];
users?: string[];
/** For replies, whether to mention the author of the message being replied to (default false) */
repliedUser: boolean;
repliedUser?: boolean;
}
/** https://discord.com/developers/docs/resources/channel#allowed-mentions-object */

View File

@@ -1,6 +1,7 @@
import { Embed } from "../embeds/embed.ts";
import { AllowedMentions } from "../messages/allowed_mentions.ts";
import { MessageReference } from "../messages/message_reference.ts";
import { FileContent } from "../misc/file_content.ts";
import { SnakeCaseProps } from "../util.ts";
export interface CreateMessage {
@@ -16,7 +17,9 @@ export interface CreateMessage {
allowedMentions?: AllowedMentions;
/** Include to make your message a reply */
messageReference?: MessageReference;
/** The contents of the file being sent */
file?: FileContent | FileContent[];
}
/** https://discord.com/developers/docs/resources/channel#create-message */
export type DiscordCreateMessage = SnakeCaseProps<CreateMessage>;
export type DiscordCreateMessage = SnakeCaseProps<Omit<CreateMessage, "file">>;

View File

@@ -0,0 +1,17 @@
import { Embed } from "../embeds/embed.ts";
import { SnakeCaseProps } from "../util.ts";
import { AllowedMentions } from "./allowed_mentions.ts";
export interface EditMessage {
/** The new message contents (up to 2000 characters) */
content?: string | null;
/** Embedded `rich` content */
embed?: Embed | null;
/** Edit the flags of the message (only `SUPRESS_EMBEDS` can currently be set/unset) */
flags?: 4 | null;
/** Allowed mentions for the message */
allowedMentions?: AllowedMentions | null;
}
/** https://discord.com/developers/docs/resources/channel#edit-message-json-params */
export type DiscordEditMessage = SnakeCaseProps<EditMessage>;