import {z} from 'zod' export type SnowflakeType = unknown | number; export type MessageContentRequest = string; export type ColorType = number; export type RichEmbedAuthorRequest = {name: string, url?: (string | null) | undefined, icon_url?: (string | null) | undefined} | null; export type RichEmbedMediaRequest = {url: string, description?: (string | null) | undefined} | null; export type RichEmbedFooterRequest = {text: string, icon_url?: (string | null) | undefined} | null; export type RichEmbedRequest = {url?: (string | null) | undefined, title?: (string | null) | undefined, color?: (ColorType | null) | undefined, timestamp?: (string | number | null) | undefined, description?: (string | null) | undefined, author?: (RichEmbedAuthorRequest | null) | undefined, image?: (RichEmbedMediaRequest | null) | undefined, thumbnail?: (RichEmbedMediaRequest | null) | undefined, footer?: (RichEmbedFooterRequest | null) | undefined, fields?: (Array<{name: string, value: string, inline?: boolean | undefined}> | null) | undefined}; export type MessageAttachmentFlags = number; export type Int32Type = number; export type NonNegativeSafeIntegerType = number; export type ClientUploadedAttachmentRequest = {title?: (string | null) | undefined, description?: (string | null) | undefined, flags?: MessageAttachmentFlags | undefined, duration?: (Int32Type | null) | undefined, waveform?: (string | null) | undefined, id: Int32Type, filename: string, content_type: string, upload_filename: string, file_size: NonNegativeSafeIntegerType}; export type ClientAttachmentRequest = {title?: (string | null) | undefined, description?: (string | null) | undefined, flags?: MessageAttachmentFlags | undefined, duration?: (Int32Type | null) | undefined, waveform?: (string | null) | undefined, id: Int32Type, filename: string, content_type?: string | undefined}; export type MessageReferenceTypeInput = 0 | 1; export type MessageReferenceRequest = {message_id: SnowflakeType, channel_id?: SnowflakeType | undefined, guild_id?: SnowflakeType | undefined, type?: MessageReferenceTypeInput | undefined, attachment_ids?: Array | undefined, embed_indices?: Array | undefined}; export type AllowedMentionsRequest = {parse?: (Array<'users' | 'roles' | 'everyone'>) | undefined, users?: Array | undefined, roles?: Array | undefined, replied_user?: boolean | undefined}; export type MessageFlags = number; export type MessageNonceRequest = string | number; export type MessageRequestSchema = {content?: (MessageContentRequest | null) | undefined, embeds?: Array | undefined, attachments?: (Array) | undefined, message_reference?: (MessageReferenceRequest | null) | undefined, allowed_mentions?: (AllowedMentionsRequest | null) | undefined, flags?: MessageFlags | undefined, nonce?: MessageNonceRequest | undefined, favorite_meme_id?: (SnowflakeType | null) | undefined, sticker_ids?: (Array | null) | undefined, tts?: boolean | undefined}; export type CreateApiChannelsChannelIdMessagesArgs = {channel_id: SnowflakeType, body: MessageRequestSchema}; export type CreateApiChannelsChannelIdMessagesOptions = {baseUrl?: string | undefined, botToken?: string | undefined, fetch?: typeof fetch | undefined}; export const snowflakeStringType = z.string(); export const int32Type = z.number().int().gte(0).lte(2147483647); export const publicUserFlags = z.number().int().gte(0).lte(2147483647); export const mentionReplyPreferences = z.union([z.literal(0), z.literal(1), z.literal(2)]); export const userPartialResponse = z.object({id: snowflakeStringType, username: z.string(), discriminator: z.string(), global_name: z.string().nullable(), avatar: z.string().nullable(), avatar_color: int32Type.nullable(), bot: z.boolean().optional(), system: z.boolean().optional(), flags: publicUserFlags, mention_flags: mentionReplyPreferences.optional()}); export const messageType = z.union([z.literal(0), z.literal(1), z.literal(2), z.literal(3), z.literal(4), z.literal(5), z.literal(6), z.literal(7), z.literal(12), z.literal(18), z.literal(19), z.literal(21)]); export const messageFlags = z.number().int().gte(0).lte(2147483647); export const messageChannelMentionResponse = z.object({id: snowflakeStringType, name: z.string(), type: int32Type}); export const embedAuthorResponse = z.object({name: z.string(), url: z.string().nullable().optional(), icon_url: z.string().nullable().optional(), proxy_icon_url: z.string().nullable().optional()}); export const embedMediaFlags = z.number().int().gte(0).lte(2147483647); export const embedMediaResponse = z.object({url: z.string(), proxy_url: z.string().nullable().optional(), content_type: z.string().nullable().optional(), content_hash: z.string().nullable().optional(), width: int32Type.nullable().optional(), height: int32Type.nullable().optional(), description: z.string().nullable().optional(), placeholder: z.string().nullable().optional(), duration: int32Type.nullable().optional(), flags: embedMediaFlags}); export const embedFooterResponse = z.object({text: z.string(), icon_url: z.string().nullable().optional(), proxy_icon_url: z.string().nullable().optional()}); export const embedFieldResponse = z.object({name: z.string(), value: z.string(), inline: z.boolean()}); export const embedProviderResponse = z.object({name: z.string(), url: z.string().nullable().optional()}); export const messageEmbedChildResponse = z.object({type: z.string(), url: z.string().nullable().optional(), title: z.string().nullable().optional(), color: int32Type.nullable().optional(), timestamp: z.string().nullable().optional(), description: z.string().nullable().optional(), author: embedAuthorResponse.nullable().optional(), image: embedMediaResponse.nullable().optional(), thumbnail: embedMediaResponse.nullable().optional(), footer: embedFooterResponse.nullable().optional(), fields: z.array(embedFieldResponse).nullable().optional(), provider: embedProviderResponse.nullable().optional(), video: embedMediaResponse.nullable().optional(), audio: embedMediaResponse.nullable().optional(), html: z.string().nullable().optional(), html_width: int32Type.nullable().optional(), html_height: int32Type.nullable().optional(), nsfw: z.boolean().nullable().optional()}); export const messageEmbedResponse = z.object({type: z.string(), url: z.string().nullable().optional(), title: z.string().nullable().optional(), color: int32Type.nullable().optional(), timestamp: z.string().nullable().optional(), description: z.string().nullable().optional(), author: embedAuthorResponse.nullable().optional(), image: embedMediaResponse.nullable().optional(), thumbnail: embedMediaResponse.nullable().optional(), footer: embedFooterResponse.nullable().optional(), fields: z.array(embedFieldResponse).nullable().optional(), provider: embedProviderResponse.nullable().optional(), video: embedMediaResponse.nullable().optional(), audio: embedMediaResponse.nullable().optional(), html: z.string().nullable().optional(), html_width: int32Type.nullable().optional(), html_height: int32Type.nullable().optional(), nsfw: z.boolean().nullable().optional(), children: z.array(messageEmbedChildResponse).nullable().optional()}); export const nonNegativeSafeIntegerType = z.number().int().gte(0).lte(9007199254740991); export const messageAttachmentFlags = z.number().int().gte(0).lte(2147483647); export const messageAttachmentResponse = z.object({id: snowflakeStringType, filename: z.string(), title: z.string().nullable().optional(), description: z.string().nullable().optional(), content_type: z.string().nullable().optional(), content_hash: z.string().nullable().optional(), size: nonNegativeSafeIntegerType, url: z.string().nullable().optional(), proxy_url: z.string().nullable().optional(), width: int32Type.nullable().optional(), height: int32Type.nullable().optional(), placeholder: z.string().nullable().optional(), flags: messageAttachmentFlags, nsfw: z.boolean().nullable().optional(), duration: int32Type.nullable().optional(), waveform: z.string().nullable().optional(), expires_at: z.string().nullable().optional(), expired: z.boolean().nullable().optional()}); export const messageStickerResponse = z.object({id: snowflakeStringType, name: z.string(), animated: z.boolean()}); export const messageReactionResponse = z.object({emoji: z.object({id: snowflakeStringType.nullable().optional(), name: z.string(), animated: z.boolean().nullable().optional()}), count: int32Type, me: z.boolean().nullable().optional()}); export const messageReferenceType = z.union([z.literal(0), z.literal(1)]); export const messageSnapshotResponse = z.object({content: z.string().nullable().optional(), timestamp: z.string(), edited_timestamp: z.string().nullable().optional(), mentions: z.array(z.string()).nullable().optional(), mention_roles: z.array(z.string()).nullable().optional(), mention_channels: z.array(messageChannelMentionResponse).nullable().optional(), embeds: z.array(messageEmbedResponse).nullable().optional(), attachments: z.array(messageAttachmentResponse).nullable().optional(), stickers: z.array(messageStickerResponse).nullable().optional(), type: messageType, flags: messageFlags}); export const channelType = z.union([z.literal(0), z.literal(1), z.literal(2), z.literal(3), z.literal(4), z.literal(5), z.literal(10), z.literal(11), z.literal(12), z.literal(15), z.literal(16), z.literal(998), z.literal(999)]); export const channelOverwriteType = z.union([z.literal(0), z.literal(1)]); export const permissions = z.string(); export const channelOverwriteResponse = z.object({id: snowflakeStringType, type: channelOverwriteType, allow: permissions, deny: permissions}); export const contentWarningLevel = z.union([z.literal(0), z.literal(1)]); export const threadMetadataResponse = z.object({archived: z.boolean(), auto_archive_duration: int32Type, archive_timestamp: z.string(), locked: z.boolean(), invitable: z.boolean().optional(), create_timestamp: z.string()}); export const guildMemberProfileFlags = z.number().int().gte(0).lte(2147483647); export const guildMemberResponse = z.object({user: userPartialResponse, nick: z.string().nullable().optional(), avatar: z.string().nullable().optional(), banner: z.string().nullable().optional(), accent_color: int32Type.nullable().optional(), roles: z.array(z.string()), joined_at: z.string(), mute: z.boolean(), deaf: z.boolean(), communication_disabled_until: z.string().nullable().optional(), profile_flags: guildMemberProfileFlags.nullable().optional(), mention_flags: mentionReplyPreferences.nullable().optional()}); export const threadMemberResponse = z.object({id: snowflakeStringType.optional(), user_id: snowflakeStringType.optional(), join_timestamp: z.string(), flags: int32Type, muted: z.boolean().optional(), mute_config: z.object({end_time: z.string().nullable(), selected_time_window: int32Type}).nullable().optional(), member: guildMemberResponse.optional()}); export const forumTagResponse = z.object({id: snowflakeStringType, name: z.string().max(50), moderated: z.boolean(), emoji_id: snowflakeStringType.nullable(), emoji_name: z.string().nullable()}); export const defaultReactionEmojiResponse = z.object({emoji_id: snowflakeStringType.nullable(), emoji_name: z.string().nullable()}); export const threadChannelResponse = z.object({id: snowflakeStringType, guild_id: snowflakeStringType.optional(), name: z.string().nullable().optional(), topic: z.string().nullable().optional(), url: z.string().nullable().optional(), icon: z.string().nullable().optional(), owner_id: snowflakeStringType.nullable().optional(), type: channelType, position: int32Type.optional(), parent_id: snowflakeStringType.nullable().optional(), bitrate: int32Type.nullable().optional(), user_limit: int32Type.nullable().optional(), voice_connection_limit: int32Type.nullable().optional(), rtc_region: z.string().nullable().optional(), rtc_p2p: z.boolean().optional(), last_message_id: snowflakeStringType.nullable().optional(), last_pin_timestamp: z.string().nullable().optional(), permission_overwrites: z.array(channelOverwriteResponse).optional(), recipients: z.array(userPartialResponse).optional(), nsfw: z.boolean().optional(), nsfw_override: z.boolean().nullable().optional(), content_warning_level: contentWarningLevel.optional(), content_warning_text: z.string().max(200).nullable().optional(), rate_limit_per_user: int32Type.optional(), nicks: z.record(z.string(), z.string().min(1).max(32)).optional(), flags: int32Type.optional(), thread_metadata: threadMetadataResponse.optional(), applied_tags: z.array(snowflakeStringType).optional(), message_count: int32Type.optional(), total_message_sent: int32Type.optional(), member_count: int32Type.optional(), member_ids_preview: z.array(snowflakeStringType).optional(), member: threadMemberResponse.optional(), default_auto_archive_duration: int32Type.nullable().optional(), default_thread_rate_limit_per_user: int32Type.optional(), available_tags: z.array(forumTagResponse).optional(), default_reaction_emoji: defaultReactionEmojiResponse.nullable().optional(), default_sort_order: int32Type.nullable().optional(), default_forum_layout: int32Type.optional(), default_tag_setting: z.enum(["match_some", "match_all"]).optional()}); export const messageResponseSchema = z.object({id: snowflakeStringType, channel_id: snowflakeStringType, author: userPartialResponse, webhook_id: snowflakeStringType.nullable().optional(), type: messageType, flags: messageFlags, content: z.string(), timestamp: z.string(), edited_timestamp: z.string().nullable().optional(), pinned: z.boolean(), mention_everyone: z.boolean(), tts: z.boolean(), mentions: z.array(userPartialResponse), mention_roles: z.array(z.string()), mention_channels: z.array(messageChannelMentionResponse).nullable().optional(), users: z.array(userPartialResponse).nullable().optional(), embeds: z.array(messageEmbedResponse).nullable().optional(), attachments: z.array(messageAttachmentResponse).nullable().optional(), stickers: z.array(messageStickerResponse).nullable().optional(), reactions: z.array(messageReactionResponse).nullable().optional(), message_reference: z.object({channel_id: snowflakeStringType, message_id: snowflakeStringType.nullable().optional(), guild_id: snowflakeStringType.nullable().optional(), type: messageReferenceType}).nullable().optional(), message_snapshots: z.array(messageSnapshotResponse).nullable().optional(), nonce: z.string().nullable().optional(), call: z.object({participants: z.array(z.string()), ended_timestamp: z.string().nullable().optional()}).nullable().optional(), thread: threadChannelResponse.optional(), referenced_message: z.object({id: snowflakeStringType, channel_id: snowflakeStringType, author: userPartialResponse, webhook_id: snowflakeStringType.nullable().optional(), type: messageType, flags: messageFlags, content: z.string(), timestamp: z.string(), edited_timestamp: z.string().nullable().optional(), pinned: z.boolean(), mention_everyone: z.boolean(), tts: z.boolean(), mentions: z.array(userPartialResponse), mention_roles: z.array(z.string()), mention_channels: z.array(messageChannelMentionResponse).nullable().optional(), users: z.array(userPartialResponse).nullable().optional(), embeds: z.array(messageEmbedResponse).nullable().optional(), attachments: z.array(messageAttachmentResponse).nullable().optional(), stickers: z.array(messageStickerResponse).nullable().optional(), reactions: z.array(messageReactionResponse).nullable().optional(), message_reference: z.object({channel_id: snowflakeStringType, message_id: snowflakeStringType.nullable().optional(), guild_id: snowflakeStringType.nullable().optional(), type: messageReferenceType}).nullable().optional(), message_snapshots: z.array(messageSnapshotResponse).nullable().optional(), nonce: z.string().nullable().optional(), call: z.object({participants: z.array(z.string()), ended_timestamp: z.string().nullable().optional()}).nullable().optional(), thread: threadChannelResponse.optional()}).nullable().optional()}); export const validateResponse = async ( schema: { readonly '~standard': { readonly validate: (value: unknown) => ({ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }) | Promise<{ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }> } }, value: unknown ): Promise => { const result = await schema['~standard'].validate(value) if (result.issues !== undefined) { const detail = result.issues .map(({ message, path }) => path?.length ? `${path.map((segment) => String(typeof segment === 'object' ? segment.key : segment)).join('.')}: ${message}` : message ) .join('; ') throw new Error(`Response does not match the schema: ${detail}`, { cause: { issues: result.issues } }) } return result.value }; /** * Send a message * * POST /channels/{channel_id}/messages * * Also accepts auth: sessionToken */ export const createApiChannelsChannelIdMessages = async (args: CreateApiChannelsChannelIdMessagesArgs, options?: CreateApiChannelsChannelIdMessagesOptions) => { const {baseUrl = "https://web.fluxer.app/api/v1", fetch: fetchFn = fetch, botToken} = options ?? {} const query = new URLSearchParams() const headers = new Headers() headers.set('content-type', "application/json") headers.set('accept', "application/json") if (botToken !== undefined) headers.set("Authorization", botToken) const url = `${baseUrl.replace(/\/+$/, '')}/channels/${encodeURIComponent(String(args.channel_id))}/messages${query.size > 0 ? `?${query}` : ''}` const res = await fetchFn(url, {method: "POST", headers, body: JSON.stringify(args.body)}) if (!res.ok) throw new Error(`Request failed with status ${res.status}`, {cause: {status: res.status, body: await res.text()}}) return validateResponse(messageResponseSchema, await res.json()) };