-
-
Notifications
You must be signed in to change notification settings - Fork 4k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
efa16a6
commit 7488507
Showing
10 changed files
with
546 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
141 changes: 141 additions & 0 deletions
141
packages/discord.js/src/managers/ApplicationEmojiManager.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,141 @@ | ||
'use strict'; | ||
|
||
const { Collection } = require('@discordjs/collection'); | ||
const { Routes } = require('discord-api-types/v10'); | ||
const BaseApplicationEmojiManager = require('./BaseApplicationEmojiManager'); | ||
const { DiscordjsTypeError, ErrorCodes } = require('../errors'); | ||
const { resolveImage } = require('../util/DataResolver'); | ||
|
||
/** | ||
* Manages API methods for ApplicationEmojis and stores their cache. | ||
* @extends {BaseApplicationEmojiManager} | ||
*/ | ||
class ApplicationEmojiManager extends BaseApplicationEmojiManager { | ||
constructor(application, iterable) { | ||
super(application.client, iterable); | ||
|
||
/** | ||
* The application this manager belongs to | ||
* @type {ClientApplication} | ||
*/ | ||
this.application = application; | ||
} | ||
|
||
_add(data, cache) { | ||
return super._add(data, cache, { extras: [this.application] }); | ||
} | ||
|
||
/** | ||
* Options used for creating an emoji of an application. | ||
* @typedef {Object} ApplicationEmojiCreateOptions | ||
* @property {BufferResolvable|Base64Resolvable} attachment The image for the emoji | ||
* @property {string} name The name for the emoji | ||
*/ | ||
|
||
/** | ||
* Creates a new custom emoji in the application. | ||
* @param {ApplicationEmojiCreateOptions} options Options for creating the emoji | ||
* @returns {Promise<Emoji>} The created emoji | ||
* @example | ||
* // Create a new emoji from a URL | ||
* application.emojis.create({ attachment: 'https://i.imgur.com/w3duR07.png', name: 'rip' }) | ||
* .then(emoji => console.log(`Created new emoji with name ${emoji.name}!`)) | ||
* .catch(console.error); | ||
* @example | ||
* // Create a new emoji from a file on your computer | ||
* application.emojis.create({ attachment: './memes/banana.png', name: 'banana' }) | ||
* .then(emoji => console.log(`Created new emoji with name ${emoji.name}!`)) | ||
* .catch(console.error); | ||
*/ | ||
async create({ attachment, name }) { | ||
attachment = await resolveImage(attachment); | ||
if (!attachment) throw new DiscordjsTypeError(ErrorCodes.ReqResourceType); | ||
|
||
const body = { image: attachment, name }; | ||
|
||
const emoji = await this.client.rest.post(Routes.applicationEmojis(this.application.id), { body }); | ||
return this._add(emoji); | ||
} | ||
|
||
/** | ||
* Obtains one or more emojis from Discord, or the emoji cache if they're already available. | ||
* @param {Snowflake} [id] The emoji's id | ||
* @param {BaseFetchOptions} [options] Additional options for this fetch | ||
* @returns {Promise<ApplicationEmoji|Collection<Snowflake, ApplicationEmoji>>} | ||
* @example | ||
* // Fetch all emojis from the application | ||
* message.application.emojis.fetch() | ||
* .then(emojis => console.log(`There are ${emojis.size} emojis.`)) | ||
* .catch(console.error); | ||
* @example | ||
* // Fetch a single emoji | ||
* message.application.emojis.fetch('222078108977594368') | ||
* .then(emoji => console.log(`The emoji name is: ${emoji.name}`)) | ||
* .catch(console.error); | ||
*/ | ||
async fetch(id, { cache = true, force = false } = {}) { | ||
if (id) { | ||
if (!force) { | ||
const existing = this.cache.get(id); | ||
if (existing) return existing; | ||
} | ||
const emoji = await this.client.rest.get(Routes.applicationEmoji(this.application.id, id)); | ||
return this._add(emoji, cache); | ||
} | ||
|
||
const { items: data } = await this.client.rest.get(Routes.applicationEmojis(this.application.id)); | ||
const emojis = new Collection(); | ||
for (const emoji of data) emojis.set(emoji.id, this._add(emoji, cache)); | ||
return emojis; | ||
} | ||
|
||
/** | ||
* Deletes an emoji. | ||
* @param {EmojiResolvable} emoji The Emoji resolvable to delete | ||
* @returns {Promise<void>} | ||
*/ | ||
async delete(emoji) { | ||
const id = this.resolveId(emoji); | ||
if (!id) throw new DiscordjsTypeError(ErrorCodes.InvalidType, 'emoji', 'EmojiResolvable', true); | ||
await this.client.rest.delete(Routes.applicationEmoji(this.application.id, id)); | ||
} | ||
|
||
/** | ||
* Edits an emoji. | ||
* @param {EmojiResolvable} emoji The Emoji resolvable to edit | ||
* @param {ApplicationEmojiEditOptions} options The options to provide | ||
* @returns {Promise<ApplicationEmoji>} | ||
*/ | ||
async edit(emoji, options) { | ||
const id = this.resolveId(emoji); | ||
if (!id) throw new DiscordjsTypeError(ErrorCodes.InvalidType, 'emoji', 'EmojiResolvable', true); | ||
|
||
const newData = await this.client.rest.patch(Routes.applicationEmoji(this.application.id, id), { | ||
body: { | ||
name: options.name, | ||
}, | ||
}); | ||
const existing = this.cache.get(id); | ||
if (existing) { | ||
const clone = existing._clone(); | ||
clone._patch(newData); | ||
return clone; | ||
} | ||
return this._add(newData); | ||
} | ||
|
||
/** | ||
* Fetches the author for this emoji | ||
* @param {EmojiResolvable} emoji The emoji to fetch the author of | ||
* @returns {Promise<User>} | ||
*/ | ||
async fetchAuthor(emoji) { | ||
const emojiId = typeof emoji === 'string' ? emoji : emoji.id; | ||
|
||
const data = await this.client.rest.get(Routes.applicationEmoji(this.application.id, emojiId)); | ||
|
||
return this._add(data).author; | ||
} | ||
} | ||
|
||
module.exports = ApplicationEmojiManager; |
80 changes: 80 additions & 0 deletions
80
packages/discord.js/src/managers/BaseApplicationEmojiManager.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,80 @@ | ||
'use strict'; | ||
|
||
const CachedManager = require('./CachedManager'); | ||
const ApplicationEmoji = require('../structures/ApplicationEmoji'); | ||
const ReactionEmoji = require('../structures/ReactionEmoji'); | ||
const { parseEmoji } = require('../util/Util'); | ||
|
||
/** | ||
* Holds methods to resolve ApplicationEmojis and stores their cache. | ||
* @extends {CachedManager} | ||
*/ | ||
class BaseApplicationEmojiManager extends CachedManager { | ||
constructor(client, iterable) { | ||
super(client, ApplicationEmoji, iterable); | ||
} | ||
|
||
/** | ||
* The cache of ApplicationEmojis | ||
* @type {Collection<Snowflake, ApplicationEmoji>} | ||
* @name BaseApplicationEmojiManager#cache | ||
*/ | ||
|
||
/** | ||
* Data that can be resolved into a ApplicationEmoji object. This can be: | ||
* * A Snowflake | ||
* * An ApplicationEmoji object | ||
* * A ReactionEmoji object | ||
* @typedef {Snowflake|ApplicationEmoji|ReactionEmoji} EmojiResolvable | ||
*/ | ||
|
||
/** | ||
* Resolves an EmojiResolvable to an Emoji object. | ||
* @param {EmojiResolvable} emoji The Emoji resolvable to identify | ||
* @returns {?ApplicationEmoji} | ||
*/ | ||
resolve(emoji) { | ||
if (emoji instanceof ReactionEmoji) return super.resolve(emoji.id); | ||
return super.resolve(emoji); | ||
} | ||
|
||
/** | ||
* Resolves an EmojiResolvable to an Emoji id string. | ||
* @param {EmojiResolvable} emoji The Emoji resolvable to identify | ||
* @returns {?Snowflake} | ||
*/ | ||
resolveId(emoji) { | ||
if (emoji instanceof ReactionEmoji) return emoji.id; | ||
return super.resolveId(emoji); | ||
} | ||
|
||
/** | ||
* Data that can be resolved to give an emoji identifier. This can be: | ||
* * An EmojiResolvable | ||
* * The `<a:name:id>`, `<:name:id>`, `a:name:id` or `name:id` emoji identifier string of an emoji | ||
* * The Unicode representation of an emoji | ||
* @typedef {string|EmojiResolvable} EmojiIdentifierResolvable | ||
*/ | ||
|
||
/** | ||
* Resolves an EmojiResolvable to an emoji identifier. | ||
* @param {EmojiIdentifierResolvable} emoji The emoji resolvable to resolve | ||
* @returns {?string} | ||
*/ | ||
resolveIdentifier(emoji) { | ||
const emojiResolvable = this.resolve(emoji); | ||
if (emojiResolvable) return emojiResolvable.identifier; | ||
if (emoji instanceof ReactionEmoji) return emoji.identifier; | ||
if (typeof emoji === 'string') { | ||
const res = parseEmoji(emoji); | ||
if (res?.name.length) { | ||
emoji = `${res.animated ? 'a:' : ''}${res.name}${res.id ? `:${res.id}` : ''}`; | ||
} | ||
if (!emoji.includes('%')) return encodeURIComponent(emoji); | ||
return emoji; | ||
} | ||
return null; | ||
} | ||
} | ||
|
||
module.exports = BaseApplicationEmojiManager; |
Oops, something went wrong.