├── .gitignore ├── README.md ├── commands └── information │ └── ping.js ├── configuration ├── choices.js ├── common.js └── config.json.example ├── events └── client │ ├── interactionCreate.js │ ├── messageCreate.js │ └── ready.js ├── index.js ├── package.json └── slashcommands ├── generative ├── faceswap.js └── imagine.js └── information └── ping.js /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | package-lock.json 3 | configuration/config.json 4 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # **About** 2 | This bot can generate images using prodia with tons of models and features. 3 | 4 | ## **Used Resource** 5 | 6 | **[prodia.js](https://github.com/unburn/prodia.js) [discord.js](https://github.com/discordjs) [discord-handler](https://github.com/ogshree/discord-handler)** 7 | 8 | # **Installation** 9 | 10 | Install all packages required to run the bot. 11 | ``` 12 | npm install 13 | ``` 14 | 15 | Go to configuration folder and fill the require values and also rename **config.json.example** -> **config.json**, get the prodia key from their [official](https://prodia.com/) site. 16 | ```json 17 | { 18 | "ClientToken": "", 19 | "ClientID": "", 20 | "ClientPrefix": ".", 21 | "DeveloperIds": [""], 22 | "ProdiaKey": "" 23 | } 24 | ``` 25 | 26 | To run the bot run the following command. 27 | ``` 28 | node index.js 29 | ``` 30 | 31 | # **Label** 32 | This project belongs to **[Unburn](https://github.com/unburn)**, and you have full rights to modify or contribute. -------------------------------------------------------------------------------- /commands/information/ping.js: -------------------------------------------------------------------------------- 1 | const { Message, Client } = require("discord.js"); 2 | 3 | const data = { 4 | name: "ping", 5 | aliases: ["ms", "ws"], 6 | } 7 | 8 | const perms = { 9 | BotPermissions: ["SendMessages"], UserPermissions: ["SendMessages"], devOnly: false 10 | } 11 | 12 | /** 13 | * @param {Client} client; 14 | * @param {Message} message; 15 | * @param {*} args; 16 | * @returns; 17 | * 18 | */ 19 | 20 | async function callback(client, message, args) { 21 | return message.reply({ content: `Ping: ${client.ws.ping}ms` }); 22 | } 23 | 24 | module.exports = { data, perms, callback } -------------------------------------------------------------------------------- /configuration/choices.js: -------------------------------------------------------------------------------- 1 | const styles = [ 2 | { name: "3d-model", value: "3d-model" }, 3 | { name: "analog-film", value: "analog-film" }, 4 | { name: "anime", value: "anime" }, 5 | { name: "cinematic", value: "cinematic" }, 6 | { name: "comic-book", value: "comic-book" }, 7 | { name: "digital-art", value: "digital-art" }, 8 | { name: "enhance", value: "enhance" }, 9 | { name: "fantasty-art", value: "fantasty-art" }, 10 | { name: "isometric", value: "isometric" }, 11 | { name: "line-art", value: "line-art" }, 12 | { name: "low-poly", value: "low-poly" }, 13 | { name: "neon-punk", value: "neon-punk" }, 14 | { name: "origami", value: "origami" }, 15 | { name: "photographic", value: "photographic" }, 16 | { name: "pixel-art", value: "pixel-art" }, 17 | { name: "texture", value: "texture" }, 18 | { name: "craft-clay", value: "craft-clay" } 19 | ] 20 | 21 | const samplers = [ 22 | { name: "Euler", value: "Euler" }, 23 | { name: "Euler a", value: "Euler a" }, 24 | { name: "LMS", value: "LMS" }, 25 | { name: "Heun", value: "Heun" }, 26 | { name: "DPM2", value: "DPM2" }, 27 | { name: "DPM2 a", value: "DPM2 a" }, 28 | { name: "DPM++ 2S a", value: "DPM++ 2S a" }, 29 | { name: "DPM++ 2M", value: "DPM++ 2M" }, 30 | { name: "DPM++ SDE", value: "DPM++ SDE" }, 31 | { name: "DPM fast", value: "DPM fast" }, 32 | { name: "DPM adaptive", value: "DPM adaptive" }, 33 | { name: "LMS Karras", value: "LMS Karras" }, 34 | { name: "DPM2 Karras", value: "DPM2 Karras" }, 35 | { name: "DPM2 a Karras", value: "DPM2 a Karras" }, 36 | { name: "DPM++ 2S a Karras", value: "DPM++ 2S a Karras" }, 37 | { name: "DPM++ 2M Karras", value: "DPM++ 2M Karras" }, 38 | { name: "DPM++ SDE Karras", value: "DPM++ SDE Karras" }, 39 | { name: "DDIM", value: "DDIM" }, 40 | { name: "PLMS", value: "PLMS" } 41 | ] 42 | 43 | const aspectRatio = [ 44 | { name: "landscape", value: "landscape" }, 45 | { name: "portrait", value: "portrait" }, 46 | { name: "square", value: "square" } 47 | ] 48 | 49 | module.exports = { styles, samplers, aspectRatio } -------------------------------------------------------------------------------- /configuration/common.js: -------------------------------------------------------------------------------- 1 | const resetColor = "\x1b[0m"; 2 | 3 | const print = { 4 | reset: (text) => `${text}${resetColor}`, 5 | bright: (text) => `\x1b[1m${text}${resetColor}`, 6 | dim: (text) => `\x1b[2m${text}${resetColor}`, 7 | underscore: (text) => `\x1b[4m${text}${resetColor}`, 8 | blink: (text) => `\x1b[5m${text}${resetColor}`, 9 | reverse: (text) => `\x1b[7m${text}${resetColor}`, 10 | hidden: (text) => `\x1b[8m${text}${resetColor}`, 11 | 12 | black: (text) => `\x1b[30m${text}${resetColor}`, 13 | red: (text) => `\x1b[31m${text}${resetColor}`, 14 | green: (text) => `\x1b[32m${text}${resetColor}`, 15 | oysterpink: (text) => `\x1b[38;2;213;180;180m${text}${resetColor}`, 16 | gray: (text) => `\x1b[38;5;8m${text}${resetColor}`, 17 | yellow: (text) => `\x1b[33m${text}${resetColor}`, 18 | blue: (text) => `\x1b[34m${text}${resetColor}`, 19 | magenta: (text) => `\x1b[35m${text}${resetColor}`, 20 | cyan: (text) => `\x1b[36m${text}${resetColor}`, 21 | white: (text) => `\x1b[37m${text}${resetColor}`, 22 | 23 | bgBlack: (text) => `\x1b[40m${text}${resetColor}`, 24 | bgRed: (text) => `\x1b[41m${text}${resetColor}`, 25 | bgGreen: (text) => `\x1b[42m${text}${resetColor}`, 26 | bgYellow: (text) => `\x1b[43m${text}${resetColor}`, 27 | bgBlue: (text) => `\x1b[44m${text}${resetColor}`, 28 | bgMagenta: (text) => `\x1b[45m${text}${resetColor}`, 29 | bgCyan: (text) => `\x1b[46m${text}${resetColor}`, 30 | bgWhite: (text) => `\x1b[47m${text}${resetColor}`, 31 | }; 32 | 33 | function dateTime(d) { 34 | let offsetIST = 330; 35 | d.setMinutes(d.getMinutes() + d.getTimezoneOffset() + offsetIST); 36 | 37 | const year = String(d.getFullYear()), time = String(d.toLocaleTimeString()); 38 | let month = String(d.getMonth() + 1), day = String(d.getDate()); 39 | 40 | if (month.length < 2) month = "0" + month; 41 | if (day.length < 2) day = "0" + day; 42 | return `${year}-${month}-${day} ${time}`; 43 | } 44 | 45 | 46 | function logger(type, name, description) { 47 | let info, dis; 48 | if (type == "INFO") { info = "green"; dis = "oysterpink" } else if (type == "WARN") { info = "yellow"; dis = "red" } 49 | console.log(print.gray(`[x] ${dateTime(new Date())}`), print[`${info}`](` ${type}`), ` ${print.cyan(`${name}`.padEnd(20))} : ${print[`${dis}`](`${description}`)}`) 50 | } 51 | 52 | 53 | module.exports = { logger }; 54 | -------------------------------------------------------------------------------- /configuration/config.json.example: -------------------------------------------------------------------------------- 1 | { 2 | "ClientToken": "", 3 | "ClientID": "", 4 | "ClientPrefix": ".", 5 | "DeveloperIds": [ 6 | "" 7 | ] 8 | "ProdiaKey": "", 9 | } -------------------------------------------------------------------------------- /events/client/interactionCreate.js: -------------------------------------------------------------------------------- 1 | const { ChatInputCommandInteraction } = require("discord.js"); 2 | const client = require("../../index"); 3 | 4 | module.exports = { 5 | name: "interactionCreate", 6 | 7 | /** 8 | * @param {ChatInputCommandInteraction} interaction; 9 | * @returns; 10 | * 11 | */ 12 | 13 | callback: async (interaction) => { 14 | 15 | if (!interaction.isChatInputCommand() && !interaction.isContextMenuCommand()) return; 16 | const { user, guild, commandName, member } = interaction; 17 | 18 | if (!guild) return; 19 | 20 | const command = client.slashCommands.get(commandName); 21 | 22 | if (!command) { 23 | return interaction.reply({ content: `This commands doest't exist!`, ephemeral: true }) && client.slashCommands.delete(commandName); 24 | } 25 | 26 | if (command.perms.UserPermissions && command.perms.UserPermissions.length !== 0) { 27 | if (!member.permissions.has(command.perms.UserPermissions)) return interaction.reply({ content: `You need \`${command.perms.UserPermissions.join(", ")}\` permission(s) to execute this command!`, ephemeral: true }); 28 | } 29 | 30 | 31 | if (command.perms.BotPermissions && command.perms.BotPermissions.length !== 0) { 32 | if (!guild.members.me.permissions.has(command.perms.BotPermissions)) return interaction.reply({ content: `I need \`${command.perms.BotPermissions.join(", ")}\` permission(s) to execute this command!`, ephemeral: true }); 33 | } 34 | 35 | 36 | if (command.perms.devOnly && !client.Developer.includes(user.id)) return interaction.reply({ content: `This command is devOnly!`, ephemeral: true }); 37 | 38 | command.callback(client, interaction); 39 | } 40 | } -------------------------------------------------------------------------------- /events/client/messageCreate.js: -------------------------------------------------------------------------------- 1 | const { Message, ChannelType } = require("discord.js"); 2 | const { ClientPrefix } = require("../../configuration/config.json"); 3 | const client = require("../../index"); 4 | 5 | module.exports = { 6 | name: "messageCreate", 7 | 8 | /** 9 | * @param {Message} message; 10 | * @returns; 11 | * 12 | */ 13 | 14 | callback: async (message) => { 15 | 16 | if (message.channel.type !== ChannelType.GuildText) return; 17 | const { author, guild, member } = message; 18 | 19 | if (author.bot || !message.guild || !message.content.toLowerCase().startsWith(ClientPrefix)) return; 20 | const [cmd, ...args] = message.content.slice(ClientPrefix.length).trim().split(/ +/g); 21 | 22 | const command = client.commands.get(cmd.toLowerCase()) || client.commands.find(c => c.data.aliases?.includes(cmd.toLowerCase())); 23 | 24 | if (!command) return; 25 | 26 | if (command.perms.UserPermissions && command.perms.UserPermissions.length !== 0) { 27 | if (!member.permissions.has(command.perms.UserPermissions)) return message.reply({ content: `You need \`${command.perms.UserPermissions.join(", ")}\` permission(s) to execute this command!` }); 28 | } 29 | 30 | if (command.perms.BotPermissions && command.perms.BotPermissions.length !== 0) { 31 | if (!guild.members.me.permissions.has(command.perms.BotPermissions)) return message.reply({ content: `I need \`${command.perms.BotPermissions.join(", ")}\` permission(s) to execute this command!` }); 32 | } 33 | 34 | if (command.perms.devOnly && !client.Developer.includes(author.id)) return message.reply({ content: `This command is devOnly!` }); 35 | 36 | command.callback(client, message, args); 37 | } 38 | } -------------------------------------------------------------------------------- /events/client/ready.js: -------------------------------------------------------------------------------- 1 | const { ActivityType } = require("discord.js"); 2 | const { logger } = require("../../configuration/common.js"); 3 | const client = require("../../index"); 4 | 5 | module.exports = { 6 | name: "ready", 7 | once: true, 8 | 9 | /** 10 | * @param {Client} client 11 | * @returns; 12 | * 13 | */ 14 | 15 | callback: async () => { 16 | console.log("\n") 17 | logger("INFO", "Client", `${client.user.tag} Is Online!`) 18 | 19 | let i = 0; 20 | let statuses = ["Images"]; 21 | 22 | 23 | setInterval(() => { 24 | let status = statuses[i]; 25 | client.user.setActivity({ name: status, type: ActivityType.Playing }); 26 | i = (i + 1) % statuses.length; 27 | }, 5000); 28 | } 29 | } -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | const { Client, Partials, Collection, REST, Routes, ApplicationCommandType } = require("discord.js"); 2 | const { ClientToken, ClientID } = require("./configuration/config.json"); 3 | const { logger } = require("./configuration/common.js"); 4 | const { readdirSync } = require("fs"); 5 | 6 | const client = new Client({ 7 | intents: [ 8 | "Guilds", 9 | "GuildMembers", 10 | "GuildMessages", 11 | "MessageContent", 12 | "GuildPresences", 13 | "GuildVoiceStates", 14 | "DirectMessages", 15 | ], 16 | partials: [ 17 | Partials.Channel, 18 | Partials.Reaction, 19 | Partials.User, 20 | Partials.GuildMember, 21 | Partials.Message, 22 | ] 23 | }); 24 | 25 | client.commands = new Collection(); 26 | client.slashCommands = new Collection(); 27 | 28 | //stores models list rather than fetching everytime. 29 | client.models = new Collection(); 30 | 31 | module.exports = client; 32 | 33 | (async () => { 34 | await loadCommands(); 35 | await loadEvents(); 36 | await loadSlashCommands(); 37 | })(); 38 | 39 | process.on("unhandledRejection", (reason, p) => { 40 | console.log(reason, p) 41 | }); 42 | 43 | process.on("uncaughtException", (err, origin) => { 44 | console.log(err, origin) 45 | }); 46 | 47 | client.login(ClientToken).catch((err) => { 48 | logger("WARN", "Client", `${err}`); 49 | }); 50 | 51 | async function loadEvents() { 52 | console.log(`\n✎ ᴇᴠᴇɴᴛ-ʟᴏᴀᴅᴇʀ-ʀᴜɴɪɴɢ...`); 53 | 54 | readdirSync("./events/").forEach(async (directory) => { 55 | const events = readdirSync(`./events/${directory}`).filter((file) => file.endsWith(".js")); 56 | 57 | events.forEach(file => { 58 | const event = require(`./events/${directory}/${file}`); 59 | 60 | if (event.once) { 61 | client.once(event.name, async (...args) => { 62 | event.callback(...args) 63 | }) 64 | } else { 65 | client.on(event.name, async (...args) => { 66 | event.callback(...args) 67 | }) 68 | } 69 | 70 | logger("INFO", event.name, "Successfully Loaded."); 71 | }) 72 | }) 73 | } 74 | 75 | async function loadCommands() { 76 | console.log(`\n✎ ᴍᴇssᴀɢᴇ-ᴄᴏᴍᴍᴀɴᴅ-ʟᴏᴀᴅᴇʀ-ʀᴜɴɪɴɢ...`); 77 | 78 | readdirSync("./commands/").forEach(async (directory) => { 79 | const commands = readdirSync(`./commands/${directory}`).filter((file) => file.endsWith(".js")); 80 | 81 | commands.forEach((file) => { 82 | const command = require(`./commands/${directory}/${file}`); 83 | 84 | if (!command.data.name) return logger("WARN", file, `Missing command name.`); 85 | 86 | client.commands.set(command.data.name, command); 87 | 88 | logger("INFO", command.data.name, "Successfully Loaded."); 89 | }) 90 | }) 91 | } 92 | 93 | async function loadSlashCommands() { 94 | console.log(`\n✎ sʟᴀsʜ-ᴄᴏᴍᴍᴀɴᴅ-ʟᴏᴀᴅᴇʀ-ʀᴜɴɪɴɢ...`); 95 | 96 | if (!ClientID) { 97 | return logger("WARN", "Client", `Client ID is missing in config file.`); 98 | } 99 | 100 | const slashArray = []; 101 | readdirSync("./slashcommands/").forEach(async (directory) => { 102 | const slashCommands = readdirSync(`./slashcommands/${directory}`).filter((file) => file.endsWith(".js")); 103 | 104 | slashCommands.forEach(async (file) => { 105 | const slash = require(`./slashcommands/${directory}/${file}`); 106 | 107 | if (!slash.data.name) return logger("WARN", file, `Missing command name.`); 108 | 109 | client.slashCommands.set(slash.data.name, slash); 110 | 111 | slashArray.push(slash.data); 112 | 113 | logger("INFO", slash.data.name, "Successfully Loaded."); 114 | }) 115 | }) 116 | 117 | const rest = new REST({ version: '10' }).setToken(ClientToken); 118 | 119 | try { 120 | await rest.put(Routes.applicationCommands(ClientID), { body: slashArray }) 121 | } catch (error) { 122 | console.error(error); 123 | } 124 | } -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "ai-image-bot", 3 | "version": "1.0.1", 4 | "description": "AI image bot using discord.js and prodia", 5 | "main": "index.js", 6 | "scripts": { 7 | "test": "echo \"Error: no test specified\" && exit 1", 8 | "start": "node ." 9 | }, 10 | "engines": { 11 | "node": ">=18" 12 | }, 13 | "dependencies": { 14 | "discord.js": "^14.14.1", 15 | "prodia.js": "^2.1.5" 16 | }, 17 | "keywords": [ 18 | "discord.js", 19 | "ai-image-bot", 20 | "prodia.js", 21 | "prodia" 22 | ], 23 | "author": "FlameFace", 24 | "license": "MIT" 25 | } -------------------------------------------------------------------------------- /slashcommands/generative/faceswap.js: -------------------------------------------------------------------------------- 1 | const { ChatInputCommandInteraction, ApplicationCommandType, ApplicationCommandOptionType } = require("discord.js"); 2 | const { ProdiaKey } = require("../../configuration/config.json") 3 | 4 | const { Prodia } = require("prodia.js"); 5 | const prodia = new Prodia(ProdiaKey); 6 | 7 | const data = { 8 | type: ApplicationCommandType.ChatInput, 9 | name: "faceswap", 10 | description: "Swap face using ai.", 11 | options: [ 12 | { 13 | name: "sourceurl", 14 | description: "Original image URL. Supports JPEG and PNG formats.", 15 | type: ApplicationCommandOptionType.String, 16 | required: true 17 | }, 18 | { 19 | name: "targeturl", 20 | description: "Image containing target face URL. Supports JPEG and PNG formats.", 21 | type: ApplicationCommandOptionType.String, 22 | required: true 23 | } 24 | ] 25 | } 26 | 27 | const perms = { 28 | BotPermissions: ["SendMessages"], UserPermissions: ["SendMessages"], devOnly: false 29 | } 30 | 31 | /** 32 | * @param {ChatInputCommandInteraction}interaction; 33 | * @param {Client} client; 34 | * @returns; 35 | */ 36 | 37 | async function callback(client, interaction) { 38 | await interaction.deferReply(); 39 | 40 | const sourceUrl = interaction.options.getString("sourceurl"); 41 | const targetUrl = interaction.options.getString("targeturl"); 42 | 43 | const generate = await prodia.faceSwap({ 44 | sourceUrl: sourceUrl, 45 | targetUrl: targetUrl 46 | }); 47 | 48 | while (generate.status !== "succeeded" && generate.status !== "failed") { 49 | new Promise((resolve) => setTimeout(resolve, 250)); 50 | 51 | const job = await prodia.getJob(generate.job); 52 | 53 | if (job.status === "succeeded") { 54 | return interaction.editReply({ 55 | files: [job.imageUrl, sourceUrl, targetUrl] 56 | }) 57 | } 58 | } 59 | } 60 | 61 | module.exports = { data, perms, callback } -------------------------------------------------------------------------------- /slashcommands/generative/imagine.js: -------------------------------------------------------------------------------- 1 | const { ChatInputCommandInteraction, ApplicationCommandType, ApplicationCommandOptionType, Client } = require("discord.js"); 2 | const { aspectRatio, samplers, styles } = require("../../configuration/choices"); 3 | const { ProdiaKey } = require("../../configuration/config.json") 4 | 5 | const { Prodia } = require("prodia.js"); 6 | const prodia = new Prodia(ProdiaKey); 7 | 8 | const data = { 9 | type: ApplicationCommandType.ChatInput, 10 | name: "imagine", 11 | description: "Generate awesome images.", 12 | options: [ 13 | { 14 | name: "prompt", 15 | description: "Enter the prompt to generate image.", 16 | type: ApplicationCommandOptionType.String, 17 | required: true 18 | }, 19 | { 20 | name: "model", 21 | description: "Enter the model to get type of image.", 22 | type: ApplicationCommandOptionType.String, 23 | required: false 24 | }, 25 | { 26 | name: "negative", 27 | description: "Enter the negative prompt to avoid from image.", 28 | type: ApplicationCommandOptionType.String, 29 | required: false 30 | }, 31 | { 32 | name: "style", 33 | description: "Select style of the image to generate.", 34 | type: ApplicationCommandOptionType.String, 35 | required: false, 36 | choices: styles 37 | }, 38 | { 39 | name: "steps", 40 | description: "Enter steps require to generate image.", 41 | type: ApplicationCommandOptionType.Number, 42 | required: false 43 | }, 44 | { 45 | name: "cfg_scale", 46 | description: "Enter cfg scale to make your image more precise to prompt.", 47 | type: ApplicationCommandOptionType.Number, 48 | required: false 49 | }, 50 | { 51 | name: "sampler", 52 | description: "Select sampler.", 53 | type: ApplicationCommandOptionType.String, 54 | required: false, 55 | choices: samplers 56 | }, 57 | { 58 | name: "aspect_ratio", 59 | description: "Select aspect ratio of image to generate.", 60 | type: ApplicationCommandOptionType.String, 61 | require: false, 62 | choices: aspectRatio 63 | } 64 | ] 65 | } 66 | 67 | const perms = { 68 | BotPermissions: ["SendMessages"], UserPermissions: ["SendMessages"], devOnly: false 69 | } 70 | 71 | /** 72 | * @param {ChatInputCommandInteraction}interaction; 73 | * @param {Client} client; 74 | * @returns; 75 | */ 76 | 77 | async function callback(client, interaction) { 78 | await interaction.deferReply(); 79 | 80 | const prompt = interaction.options.getString("prompt"), 81 | model = interaction.options.getString("model") || "absolutereality_v181.safetensors [3d9d4d2b]", 82 | negative_prompt = interaction.options.getString("negative"), 83 | style_preset = interaction.options.getString("style"), 84 | steps = interaction.options.getNumber("steps"), 85 | cfg_scale = interaction.options.getNumber("cfg_scale"), 86 | sampler = interaction.options.getString("sampler"), 87 | aspect_ratio = interaction.options.getString("aspect_ratio"); 88 | 89 | // This will store all models name in collection rather fetching every time. 90 | if (!client.models.get("sd")) { 91 | client.models.set("sd", await prodia.getSDmodels()) 92 | } 93 | 94 | if (!client.models.get("sd").includes(model)) return interaction.followUp({ 95 | content: "No such model.", 96 | ephemeral: true 97 | }); 98 | 99 | // Generating image... 100 | const generate = await prodia.generateImage({ 101 | model: model, 102 | prompt: prompt, 103 | negative_prompt: negative_prompt ? negative_prompt : 'worst quality, normal quality, low quality, low res, blurry, text, watermark, logo, banner, extra digits, cropped, jpeg artifacts, signature, username, error, sketch ,duplicate, ugly, monochrome, horror, geometry, mutation, disgusting, nsfw, nude, censored', 104 | style_preset: style_preset ? style_preset : 'enhance', 105 | steps: steps ? steps : 20, 106 | cfg_scale: cfg_scale ? cfg_scale : 9, 107 | sampler: sampler ? sampler : 'Euler a', 108 | aspect_ratio: aspect_ratio ? aspect_ratio : 'square' 109 | }); 110 | 111 | while (generate.status !== "succeeded" && generate.status !== "failed") { 112 | new Promise((resolve) => setTimeout(resolve, 250)); 113 | 114 | const job = await prodia.getJob(generate.job); 115 | 116 | if (job.status === "succeeded") { 117 | return interaction.editReply(job.imageUrl); 118 | } 119 | } 120 | } 121 | 122 | 123 | module.exports = { data, perms, callback } -------------------------------------------------------------------------------- /slashcommands/information/ping.js: -------------------------------------------------------------------------------- 1 | const { ChatInputCommandInteraction, ApplicationCommandType } = require("discord.js"); 2 | 3 | const data = { 4 | type: ApplicationCommandType.ChatInput, 5 | name: "ping", 6 | description: "display current ping dada.", 7 | } 8 | 9 | const perms = { 10 | BotPermissions: ["SendMessages"], UserPermissions: ["SendMessages"], devOnly: false 11 | } 12 | 13 | /** 14 | * @param {ChatInputCommandInteraction}interaction; 15 | * @param {Client} client; 16 | * @returns; 17 | */ 18 | 19 | async function callback(client, interaction) { 20 | return interaction.reply({ ephemeral: true, content: `${client.ws.ping}ms` }); 21 | } 22 | 23 | 24 | module.exports = { data, perms, callback } --------------------------------------------------------------------------------