Merge pull request #24 from DJj123dj/dev

v2.4.0 pre release
This commit is contained in:
Jasper
2022-08-02 14:15:24 +02:00
committed by GitHub
32 changed files with 992 additions and 394 deletions
+27 -21
View File
@@ -7,7 +7,7 @@ make a ticket in our server to start!
*if you translate, you will come in the credits*
# open-ticket
[![discord](https://img.shields.io/badge/discord-join%20our%20server-5865F2.svg?style=flat-square&logo=discord)](https://discord.com/invite/26vT9wt3n3) [![version](https://img.shields.io/badge/version-2.3.3%20stable-brightgreen.svg?style=flat-square)](https://github.com/DJj123dj/open-ticket/releases/tag/v2.3.3) [![npm](https://img.shields.io/badge/npm-external%20libraries%20needed-CB3837.svg?style=flat-square&logo=npm)](#packages) [![license](https://img.shields.io/badge/license-GPL%203.0-important.svg?style=flat-square)](https://github.com/DJj123dj/open-ticket/blob/main/LICENSE)
[![discord](https://img.shields.io/badge/discord-join%20our%20server-5865F2.svg?style=flat-square&logo=discord)](https://discord.com/invite/26vT9wt3n3) [![version](https://img.shields.io/badge/version-2.4.0%20stable-brightgreen.svg?style=flat-square)](https://github.com/DJj123dj/open-ticket/releases/tag/v2.4.0) [![npm](https://img.shields.io/badge/npm-external%20libraries%20needed-CB3837.svg?style=flat-square&logo=npm)](#packages) [![license](https://img.shields.io/badge/license-GPL%203.0-important.svg?style=flat-square)](https://github.com/DJj123dj/open-ticket/blob/main/LICENSE)
This is an open-source discord ticket bot, you can configure it and it comes with cool features like transcripts & custom options!
@@ -18,51 +18,57 @@ This is an open-source discord ticket bot, you can configure it and it comes wit
### Thanks to these people:
- DJ-Lite: for doing the administration
- Sanke: for translation & new ideas
- Everyone that reported a bug
#### And our translators!
- ExothDE: for translation
- 1x1: for translation
- R0JO: for translation
- Everyone that reported a bug
- t0miiis for translation
## features
- discord buttons
- discord interaction buttons
- slash & text commands
- close, delete & re-open tickets
- translation (we are searching for translators!)
- translation in 8 different languages
- dynamic database system
- advanced transcripts
- transcripts
- add/remove users from a ticket
- large embed customisation
- create custom ticket names, icons & colors
- create url's & reaction roles!
- uses discord.js v13
- configure your own ticket options
- remove credits if you want (don't do it please 😉)
- unlimited tickets at the same time
- custom colors & name for embeds
- customise your ticket
- create url buttons for websites
- create reaction roles
- build with discord.js v14
- configure everything per ticket
- remove credits if you want :(
- unlimited tickets spread over multiple messages
*comming soon:*
- dashboard
- view transcripts in dashboard
- share transcripts
- close with reason
- more translation
## installation
**You need `node.js 16` to run this project!**
**At this moment you still need discord.js v13!**
This will change soon!
You can clone or download this project.
### packages
- chalk => version `latest`
- discord.js => version `latest`
- express => version `latest`
- node-localstorage => version `latest`
- axios => version `latest`
You can install all of them by running `npm install`
## running
you can run `node index.js` but i would recommend you to use `npm start`
if there are any errors, you can open an **issue on github** or **contact me in the discord server**.
if there are any errors, you can open an **issue on github** or **contact me in our discord server**.
### config
Our config documentation is moved to another file:
[click here to view](https://www.github.com/DJj123dj/open-ticket/wiki/config-v2.3.3)
[click here to view](https://www.github.com/DJj123dj/open-ticket/wiki/config-v2.4.0)
### intents & permissions
In the discord developer portal in the "bot" panel you will find 3 switches under the title "Gateaway Intents". The following switches should always be turned on
@@ -74,8 +80,8 @@ You can also configure your own permissions
## information
_v2.3.3 stable_
_v2.4.0 stable_
changelog: [click here](https://www.github.com/DJj123dj/open-ticket/wiki/Changelog)
© 2022 - DJdj Development | [website](https://www.dj-dj.be) | [discord](https://discord.com/invite/26vT9wt3n3)
© 2022 - DJdj Development | [website](https://www.dj-dj.be) | [discord](https://discord.dj-dj.be) | [terms of service](https://www.dj-dj.be/terms)
+24 -9
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
client.on("messageCreate",msg => {
@@ -11,12 +14,10 @@ module.exports = () => {
var user = msg.mentions.users.first()
if (!user) return msg.channel.send({embeds:[bot.errorLog.invalidArgsMessage(l.errors.missingArgsDescription+" `<user>`:\n`"+config.prefix+"add <user>`")]})
if (!msg.member.permissions.has("ManageChannels") && !msg.member.permissions.has("Administrator") && config.main_adminroles.some((item)=>{return msg.member.roles.cache.has(item)}) == false){
try {
return msg.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return msg.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!msg.guild) return
if (!permsChecker.command(msg.author.id,msg.guild.id)){
permsChecker.sendUserNoPerms(msg.author)
return
}
msg.channel.messages.fetchPinned().then(msglist => {
@@ -30,6 +31,12 @@ module.exports = () => {
var loguser = msg.mentions.users.first()
log("command","someone used the 'add' command",[{key:"user",value:msg.author.tag}])
log("system","user added to ticket",[{key:"user",value:msg.author.tag},{key:"ticket",value:msg.channel.name},{key:"added_user",value:loguser.tag}])
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("../core/getoptions").getOptionsById("newT"+ticketId)
APIEvents.onTicketAdd(msg.author,loguser,msg.channel,msg.guild,new Date(),{status:"open",name:msg.channel.name,ticketOptions:ticketData})
APIEvents.onCommand("add",permsChecker.command(msg.author.id,msg.guild.id),msg.author,msg.channel,msg.guild,new Date())
})
})
@@ -39,12 +46,14 @@ module.exports = () => {
if (interaction.commandName != "add") return
const user = interaction.options.getUser("user")
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.reply({embeds:[bot.errorLog.noPermsMessage],ephemeral:true})
if (!interaction.guild) return
if (!permsChecker.command(interaction.user.id,interaction.guild.id)){
permsChecker.sendUserNoPerms(interaction.user)
return
}
interaction.deferReply()
interaction.channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
@@ -56,6 +65,12 @@ module.exports = () => {
var loguser = user
log("command","someone used the 'add' command",[{key:"user",value:interaction.user.tag}])
log("system","user added to ticket",[{key:"user",value:interaction.user.tag},{key:"ticket",value:interaction.channel.name},{key:"added_user",value:loguser.tag}])
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("../core/getoptions").getOptionsById("newT"+ticketId)
APIEvents.onTicketAdd(interaction.user,loguser,interaction.channel,interaction.guild,new Date(),{status:"open",name:interaction.channel.name,ticketOptions:ticketData})
APIEvents.onCommand("add",permsChecker.command(interaction.user.id,interaction.guild.id),interaction.user,interaction.channel,interaction.guild,new Date())
})
+7
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
client.on("messageCreate",msg => {
@@ -27,6 +30,7 @@ module.exports = () => {
msg.channel.send({embeds:[bot.errorLog.success(l.commands.closeTitle,l.commands.closeDescription)],components:[closebutton]})
log("command","someone used the 'close' command",[{key:"user",value:msg.author.tag}])
APIEvents.onCommand("close",true,msg.author,msg.channel,msg.guild,new Date())
})
@@ -37,6 +41,8 @@ module.exports = () => {
if (!interaction.isChatInputCommand()) return
if (interaction.commandName != "close") return
interaction.deferReply()
interaction.channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
@@ -54,6 +60,7 @@ module.exports = () => {
interaction.reply({embeds:[bot.errorLog.success(l.commands.closeTitle,l.commands.closeDescription)],components:[closebutton]})
log("command","someone used the 'close' command",[{key:"user",value:interaction.user.tag}])
APIEvents.onCommand("close",true,interaction.user,interaction.channel,interaction.guild,new Date())
})
})
+14 -10
View File
@@ -4,17 +4,18 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
client.on("messageCreate",msg => {
if (!msg.content.startsWith(config.prefix+"delete")) return
if (!msg.member.permissions.has("ManageChannels") && !msg.member.permissions.has("Administrator") && config.main_adminroles.some((item)=>{return msg.member.roles.cache.has(item)}) == false){
try {
return msg.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return msg.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!msg.guild) return
if (!permsChecker.command(msg.author.id,msg.guild.id)){
permsChecker.sendUserNoPerms(msg.author)
return
}
msg.channel.messages.fetchPinned().then(msglist => {
@@ -34,7 +35,7 @@ module.exports = () => {
msg.channel.send({embeds:[bot.errorLog.success(l.commands.deleteTitle,l.commands.deleteDescription)],components:[closebutton]})
log("command","someone used the 'delete' command",[{key:"user",value:msg.author.tag}])
APIEvents.onCommand("delete",permsChecker.command(msg.author.id,msg.guild.id),msg.author,msg.channel,msg.guild,new Date())
})
@@ -44,9 +45,11 @@ module.exports = () => {
if (!interaction.isChatInputCommand()) return
if (interaction.commandName != "delete") return
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.reply({embeds:[bot.errorLog.noPermsMessage],ephemeral:true})
interaction.deferReply()
if (!interaction.guild) return
if (!permsChecker.command(interaction.user.id,interaction.guild.id)){
permsChecker.sendUserNoPerms(interaction.user)
return
}
@@ -67,6 +70,7 @@ module.exports = () => {
interaction.reply({embeds:[bot.errorLog.success(l.commands.deleteTitle,l.commands.deleteDescription)],components:[closebutton]})
log("command","someone used the 'close' command",[{key:"user",value:interaction.user.tag}])
APIEvents.onCommand("delete",permsChecker.command(interaction.user.id,interaction.guild.id),interaction.user,interaction.channel,interaction.guild,new Date())
})
})
+5
View File
@@ -5,6 +5,8 @@ const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
const helpEmbed = new discord.EmbedBuilder()
.setColor(config.main_color)
@@ -24,6 +26,7 @@ module.exports = () => {
if (!args[1]){
msg.channel.send({embeds:[helpEmbed]})
log("command","someone used the 'help' command",[{key:"user",value:msg.author.tag}])
APIEvents.onCommand("help",true,msg.author,msg.channel,msg.guild,new Date())
return
}
@@ -31,6 +34,7 @@ module.exports = () => {
msg.channel.send({embeds:[helpEmbed]})
log("command","someone used the 'help' command",[{key:"user",value:msg.author.tag}])
APIEvents.onCommand("help",true,msg.author,msg.channel,msg.guild,new Date())
}
})
@@ -40,5 +44,6 @@ module.exports = () => {
interaction.reply({embeds:[helpEmbed]})
log("command","someone used the 'help' command",[{key:"user",value:interaction.user.tag}])
APIEvents.onCommand("help",true,interaction.user,interaction.channel,interaction.guild,new Date())
})
}
+22 -9
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
client.on("messageCreate",msg => {
@@ -11,14 +14,14 @@ module.exports = () => {
var user = msg.mentions.users.first()
if (!user) return msg.channel.send({embeds:[bot.errorLog.invalidArgsMessage(l.errors.missingArgsDescription+" `<user>`:\n`"+config.prefix+"remove <user>`")]})
if (!msg.member.permissions.has("ManageChannels") && !msg.member.permissions.has("Administrator") && config.main_adminroles.some((item)=>{return msg.member.roles.cache.has(item)}) == false){
try {
return msg.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return msg.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!msg.guild) return
if (!permsChecker.command(msg.author.id,msg.guild.id)){
permsChecker.sendUserNoPerms(msg.author)
return
}
interaction.deferReply()
msg.channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
@@ -31,6 +34,11 @@ module.exports = () => {
log("command","someone used the 'remove' command",[{key:"user",value:msg.author.tag}])
log("system","user removed from ticket",[{key:"user",value:msg.author.tag},{key:"ticket",value:msg.channel.name},{key:"removed_user",value:loguser.tag}])
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("../core/getoptions").getOptionsById("newT"+ticketId)
APIEvents.onTicketRemove(msg.author,loguser,msg.channel,msg.guild,new Date(),{status:"open",name:msg.channel.name,ticketOptions:ticketData})
APIEvents.onCommand("remove",permsChecker.command(msg.author.id,msg.guild.id),msg.author,msg.channel,msg.guild,new Date())
})
})
@@ -40,9 +48,9 @@ module.exports = () => {
if (interaction.commandName != "remove") return
const user = interaction.options.getUser("user")
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.reply({embeds:[bot.errorLog.noPermsMessage],ephemeral:true})
if (!interaction.guild) return
if (!permsChecker.command(interaction.user.id,interaction.guild.id)){
permsChecker.sendUserNoPerms(interaction.user)
return
}
@@ -60,6 +68,11 @@ module.exports = () => {
log("command","someone used the 'remove' command",[{key:"user",value:interaction.user.tag}])
log("system","user removed from ticket",[{key:"user",value:interaction.user.tag},{key:"ticket",value:interaction.channel.name},{key:"removed_user",value:loguser.tag}])
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("../core/getoptions").getOptionsById("newT"+ticketId)
APIEvents.onTicketRemove(interaction.user,loguser,interaction.channel,interaction.guild,new Date(),{status:"open",name:interaction.channel.name,ticketOptions:ticketData})
APIEvents.onCommand("remove",permsChecker.command(interaction.user.id,interaction.guild.id),interaction.user,interaction.channel,interaction.guild,new Date())
})
+14 -10
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
client.on("messageCreate",msg => {
@@ -14,12 +17,10 @@ module.exports = () => {
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return msg.channel.send({embeds:[bot.errorLog.notInATicket]})
if (!msg.member.permissions.has("ManageChannels") && !msg.member.permissions.has("Administrator") && config.main_adminroles.some((item)=>{return msg.member.roles.cache.has(item)}) == false){
try {
return msg.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return msg.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!msg.guild) return
if (!permsChecker.command(msg.author.id,msg.guild.id)){
permsChecker.sendUserNoPerms(msg.author)
return
}
var newname = msg.content.split(config.prefix+"rename")[1].substring(1)
@@ -42,7 +43,7 @@ module.exports = () => {
log("command","someone used the 'rename' command",[{key:"user",value:msg.author.tag}])
log("system","ticket renamed",[{key:"user",value:msg.author.tag},{key:"ticket",value:name},{key:"newname",value:newname}])
APIEvents.onCommand("rename",permsChecker.command(msg.author.id,msg.guild.id),msg.author,msg.channel,msg.guild,new Date())
})
@@ -52,14 +53,16 @@ module.exports = () => {
if (!interaction.isChatInputCommand()) return
if (interaction.commandName != "rename") return
interaction.deferReply()
interaction.channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id)return interaction.reply({embeds:[bot.errorLog.notInATicket]})
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.reply({embeds:[bot.errorLog.noPermsMessage],ephemeral:true})
if (!interaction.guild) return
if (!permsChecker.command(interaction.user.id,interaction.guild.id)){
permsChecker.sendUserNoPerms(interaction.user)
return
}
@@ -81,6 +84,7 @@ module.exports = () => {
log("command","someone used the 'rename' command",[{key:"user",value:interaction.user.tag}])
log("system","ticket renamed",[{key:"user",value:interaction.user.tag},{key:"ticket",value:name},{key:"newname",value:newname}])
APIEvents.onCommand("rename",permsChecker.command(interaction.user.id,interaction.guild.id),interaction.user,interaction.channel,interaction.guild,new Date())
})
})
}
+14 -3
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
var reopenCommandBar = new discord.ActionRowBuilder()
@@ -27,23 +30,31 @@ module.exports = () => {
log("command","someone used the 'reopen' command",[{key:"user",value:msg.author.tag}])
APIEvents.onCommand("reopen",true,msg.author,msg.channel,msg.guild,new Date())
})
})
client.on("interactionCreate",(interaction) => {
client.on("interactionCreate",async (interaction) => {
if (!interaction.isChatInputCommand()) return
if (interaction.commandName != "reopen") return
interaction.channel.messages.fetchPinned().then(msglist => {
await interaction.deferReply()
interaction.channel.messages.fetchPinned().then(async msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return msg.channel.send({embeds:[bot.errorLog.notInATicket]})
interaction.reply({embeds:[bot.errorLog.success(l.commands.reopenTitle,l.commands.reopenDescription)],components:[reopenCommandBar]})
try {
await interaction.reply({embeds:[bot.errorLog.success(l.commands.reopenTitle,l.commands.reopenDescription)],components:[reopenCommandBar]})
}catch{
await interaction.editReply({embeds:[bot.errorLog.success(l.commands.reopenTitle,l.commands.reopenDescription)],components:[reopenCommandBar]})
}
log("command","someone used the 'reopen' command",[{key:"user",value:interaction.user.tag}])
APIEvents.onCommand("reopen",true,interaction.user,interaction.channel,interaction.guild,new Date())
})
+15 -11
View File
@@ -4,6 +4,9 @@ const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const permsChecker = require("../core/utils/permisssionChecker")
const APIEvents = require("../core/api/modules/events")
module.exports = () => {
/**@type {String[]} */
@@ -16,12 +19,10 @@ module.exports = () => {
client.on("messageCreate", msg => {
if (msg.content.startsWith(config.prefix+"msg"||config.prefix+"message")){
if (!msg.member.permissions.has("ManageChannels") && !msg.member.permissions.has("Administrator") && config.main_adminroles.some((item)=>{return msg.member.roles.cache.has(item)}) == false){
try {
return msg.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return msg.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!msg.guild) return
if (!permsChecker.command(msg.author.id,msg.guild.id)){
permsChecker.sendUserNoPerms(msg.author)
return
}
const id = msg.content.split(config.prefix+"msg")[1].substring(1) ? msg.content.split(config.prefix+"msg")[1].substring(1) : false
@@ -34,7 +35,8 @@ module.exports = () => {
msg.channel.send({embeds:[embed],components:componentRows})
log("command","someone used the 'msg' command",[{key:"user",value:msg.author.tag},{key:"id",value:id}])
log("command","someone used the 'message' command",[{key:"user",value:msg.author.tag},{key:"id",value:id}])
APIEvents.onCommand("message",permsChecker.command(msg.author.id,msg.guild.id),msg.author,msg.channel,msg.guild,new Date())
}
})
@@ -42,9 +44,9 @@ module.exports = () => {
if (!interaction.isChatInputCommand()) return
if (interaction.commandName != "message") return
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.reply({embeds:[bot.errorLog.noPermsMessage],ephemeral:true})
if (!interaction.guild) return
if (!permsChecker.command(interaction.user.id,interaction.guild.id)){
permsChecker.sendUserNoPerms(interaction.user)
return
}
@@ -57,7 +59,9 @@ module.exports = () => {
interaction.reply({content:l.commands.ticketWarning})
interaction.channel.send({embeds:[embed],components:componentRows})
log("command","someone used the 'msg' command",[{key:"user",value:interaction.user.tag},{key:"id",value:id}])
log("command","someone used the 'message' command",[{key:"user",value:interaction.user.tag},{key:"id",value:id}])
APIEvents.onCommand("message",permsChecker.command(interaction.user.id,interaction.guild.id),interaction.user,interaction.channel,interaction.guild,new Date())
})
}
+6 -2
View File
@@ -1,5 +1,4 @@
{
"bot_name":"Wumpus",
"main_color":"#ffffff",
"server_id":"server id (for slash cmds)",
"auth_token":"auth token",
@@ -78,11 +77,16 @@
"id":"1",
"name":"Choose Your Ticket",
"description":"You can click one of the buttons below!",
"enableFooter":false,
"footer":"Open Ticket v2.3.3 - I'm a footer!",
"footer":"Open Ticket v2.4.0 - I'm a footer!",
"enableThumbnail":false,
"thumbnail":"https://www.example.com/catmemes/cat.png",
"enableCustomColor":false,
"color":"#ffffff",
"options":["general","apply"],
"enableTicketExplaination":true,
"enableMaxTicketsWarning":true
-56
View File
@@ -1,56 +0,0 @@
# OT-API Documentation
Extend open ticket with your own features!
The api is made for EXTENDING open ticket, not replacing! So with this api you are not able to replace existing features! You can only add your own features!
### DISCLAIMER:
Only edit or extend the code when you know what you are doing!
If open ticket crashes while you change the code, then we can't help you!
**DO IT ON YOUR OWN RISK!**
## Events:
Everything in the `events.js` file!
### onTicketOpen(...)
This function is executed when a new ticket is created. It happens after everything else is done, so the channel is already created!
Parameters:
- user: `discord.User`
- channel: `discord.TextChannel`
- guild: `discord.Guild`
- date: `Date`
- ticketdata: `OT TicketData` or `false` (more info further down this document)
### onTicketClose(...)
This function is executed when a ticket gets closed, it can happen multiple times with one ticket (because of reopen).
Parameters:
- user: `discord.User`
- channel: `discord.TextChannel`
- guild: `discord.Guild`
- date: `Date`
- ticketdata: `OT TicketData` or `false` (more info further down this document)
### onTicketDelete(...)
This function is executed when a ticket gets deleted, it can happen only 1 time.
Parameters:
- user: `discord.User`
- channel: `discord.TextChannel`
- guild: `discord.Guild`
- date: `Date`
- ticketdata: `OT TicketData` or `false` (more info further down this document)
### onTicketReopen(...)
...
### onTranscriptCreation(...)
...
### onCommand(...)
...
### onReactionRole(...)
...
+18
View File
@@ -0,0 +1,18 @@
//base
const bot = require("../../index")
exports.client = bot.client
exports.config = bot.config
exports.utils = {
log:bot.errorLog.log(),
storage:bot.storage
}
//events
const events = require("./modules/events").events
exports.events = events
//actions
const actions = require("./modules/actions").actions
//comming soon
//exports.actions = actions
+44 -1
View File
@@ -1,3 +1,46 @@
{
"version":"1.0.0"
"version":"1.0.0",
"disclaimer":"DISABLE doesn't work yet! Below this message!",
"disable":{
"messages":{
"ticketCreated":false,
"ticketClosed":false,
"ticketDeleted":false,
"ticketReopened":false
},
"transcripts":{
"server":false,
"dm":false
},
"commands":{
"text":{
"help":false,
"msg":false,
"close":false,
"delete":false,
"reopen":false,
"new":false,
"add":false,
"remove":false,
"rename":false
},
"slash":{
"help":false,
"msg":false,
"close":false,
"delete":false,
"reopen":false,
"new":false,
"add":false,
"remove":false,
"rename":false
}
},
"checkerjs":{
"token":false,
"all":false
}
}
}
+7
View File
@@ -0,0 +1,7 @@
//ACTIONS:
//EXPORT ACTIONS:
exports.actions = {
}
+2
View File
@@ -14,6 +14,8 @@ const storage = bot.storage
//used when creating plugins!
exports.enableApiLogs = false
//DOESN'T WORK YET
//this is used when embedding open ticket into another bot
exports.embeddedMode = false
exports.clientLocation = require("../../../index").client
-9
View File
@@ -1,9 +0,0 @@
const discord = require("discord.js")
const client = require("../../../index").client
module.exports = () => {
//this code will run when the bot starts!
}
+297 -3
View File
@@ -6,6 +6,22 @@ const log = bot.errorLog.log
const l = bot.language
const storage = bot.storage
//EVENT API:
const ticketOpenListeners = []
const ticketCloseListeners = []
const ticketDeleteListeners = []
const ticketReopenListeners = []
const ticketAddListeners = []
const ticketRemoveListeners = []
const transcriptCreationListeners = []
const commandListeners = []
const reactionRoleListeners = []
const errorListeners = []
/**
*
* @param {discord.User} user
@@ -18,7 +34,11 @@ exports.onTicketOpen = (user,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","new ticket created",[{key:"userid",value:user.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
//custom code
ticketOpenListeners.forEach((func) => {
try {
func(user,channel,guild,date,ticketdata)
}catch{}
})
}
@@ -34,7 +54,11 @@ exports.onTicketClose = (user,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","ticket closed",[{key:"userid",value:user.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
//custom code
ticketCloseListeners.forEach((func) => {
try {
func(user,channel,guild,date,ticketdata)
}catch{}
})
}
@@ -50,6 +74,276 @@ exports.onTicketDelete = (user,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","ticket deleted",[{key:"userid",value:user.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
//custom code
ticketDeleteListeners.forEach((func) => {
try {
func(user,channel,guild,date,ticketdata)
}catch{}
})
}
/**
*
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
* @param {{name:String,status:"open"|"closed"|"deleted"|"reopened",ticketOptions:Object|false}} ticketdata
*/
exports.onTicketReopen = (user,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","ticket reopened",[{key:"userid",value:user.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
ticketReopenListeners.forEach((func) => {
try {
func(user,channel,guild,date,ticketdata)
}catch{}
})
}
/**
*
* @param {discord.User} user
* @param {discord.User} editeduser
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
* @param {{name:String,status:"open"|"closed"|"deleted"|"reopened",ticketOptions:Object|false}} ticketdata
*/
exports.onTicketAdd = (user,editeduser,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","user added to ticket",[{key:"userid",value:user.id},{key:"editeduser",value:editeduser.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
ticketAddListeners.forEach((func) => {
try {
func(user,editeduser,channel,guild,date,ticketdata)
}catch{}
})
}
/**
*
* @param {discord.User} user
* @param {discord.User} editeduser
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
* @param {{name:String,status:"open"|"closed"|"deleted"|"reopened",ticketOptions:Object|false}} ticketdata
*/
exports.onTicketRemove = (user,editeduser,channel,guild,date,ticketdata) => {
//system
bot.errorLog.log("api","user removed from ticket",[{key:"userid",value:user.id},{key:"editeduser",value:editeduser.id},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id},{key:"ticketdata",value:JSON.stringify(ticketdata)}])
ticketRemoveListeners.forEach((func) => {
try {
func(user,editeduser,channel,guild,date,ticketdata)
}catch{}
})
}
/**
*
* @param {discord.Message[]} messages
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
exports.onTranscriptCreation = (messages,channel,guild,date) => {
//system
bot.errorLog.log("api","transcript created",[{key:"messages",value:JSON.stringify(messages)},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id}])
transcriptCreationListeners.forEach((func) => {
try {
func(messages,channel,guild,date)
}catch{}
})
}
/**@typedef {"help"|"message"|"close"|"delete"|"reopen"|"rename"|"add"|"remove"} OTCommandType */
/**
*
* @param {OTCommandType} type
* @param {Boolean} hasPerms
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
exports.onCommand = (type,hasPerms,user,channel,guild,date) => {
//system
bot.errorLog.log("api","someone used a command",[{key:"type",value:type},{key:"hasPerms",value:hasPerms},{key:"userid",value:user},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id}])
commandListeners.forEach((func) => {
try {
func(type,hasPerms,user,channel,guild,date)
}catch{}
})
}
/**@typedef {"add"|"remove"|"add&remove"} OTReactionRoleType */
/**@typedef {"add"|"remove"} OTReactionRoleMode */
/**
* @param {OTReactionRoleMode} mode
* @param {OTReactionRoleType} type
* @param {discord.Role} role
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
exports.onReactionRole = (mode,type,role,user,channel,guild,date) => {
//system
bot.errorLog.log("api","someone used a reaction role",[{key:"mode",value:mode},{key:"type",value:type},{key:"roleid",value:role.id},{key:"userid",value:user},{key:"channelid",value:channel.id},{key:"guildid",value:guild.id}])
reactionRoleListeners.forEach((func) => {
try {
func(mode,type,role,user,channel,guild,date)
}catch{}
})
}
/**
* @param {String} err
* @param {Date} date
*/
exports.onError = (err,date) => {
//system
bot.errorLog.log("api","there is an error",[{key:"error",value:err}])
errorListeners.forEach((func) => {
try {
func(err,date)
}catch{}
})
}
//EVENT CALLBACKS:
/**
* @callback TicketActionEvent
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
* @param {{name:String,status:"open"|"closed"|"deleted"|"reopened",ticketOptions:Object|false}} ticketdata
*/
/**
* @callback TranscriptCreationEvent
* @param {discord.Message[]} messages
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
/**
* @callback TicketUserChangeEvent
* @param {discord.User} user
* @param {discord.User} editeduser
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
* @param {{name:String,status:"open"|"closed"|"deleted"|"reopened",ticketOptions:Object|false}} ticketdata
*/
/**
* @callback CommandEvent
* @param {OTCommandType} type
* @param {Boolean} hasPerms
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
/**
* @callback ReactionRoleEvent
* @param {OTReactionRoleMode} mode
* @param {OTReactionRoleType} type
* @param {discord.Role} role
* @param {discord.User} user
* @param {discord.TextChannel} channel
* @param {discord.Guild} guild
* @param {Date} date
*/
/**
* @callback ErrorEvent
* @param {String} error
* @param {Date} date
*/
//EVENT EXPORT:
/**@param {TicketActionEvent} callback */
const onTicketOpen = (callback) => {
ticketOpenListeners.push(callback)
}
/**@param {TicketActionEvent} callback */
const onTicketClose = (callback) => {
ticketCloseListeners.push(callback)
}
/**@param {TicketActionEvent} callback */
const onTicketDelete = (callback) => {
ticketDeleteListeners.push(callback)
}
/**@param {TicketActionEvent} callback */
const onTicketReopen = (callback) => {
ticketReopenListeners.push(callback)
}
/**@param {TicketUserChangeEvent} callback */
const onTicketAdd = (callback) => {
ticketAddListeners.push(callback)
}
/**@param {TicketUserChangeEvent} callback */
const onTicketRemove = (callback) => {
ticketRemoveListeners.push(callback)
}
/**@param {TranscriptCreationEvent} callback */
const onTranscriptCreation = (callback) => {
transcriptCreationListeners.push(callback)
}
/**@param {CommandEvent} callback */
const onCommand = (callback) => {
commandListeners.push(callback)
}
/**@param {ReactionRoleEvent} callback */
const onReactionRole = (callback) => {
commandListeners.push(callback)
}
/**@param {ErrorEvent} callback */
const onError = (callback) => {
errorListeners.push(callback)
}
exports.events = {
onTicketOpen,
onTicketClose,
onTicketDelete,
onTicketReopen,
onTicketAdd,
onTicketRemove,
onTranscriptCreation,
onCommand,
onReactionRole,
onError
}
+26
View File
@@ -0,0 +1,26 @@
const fs = require("fs")
const bot = require("../../index")
const log = bot.errorLog.log
module.exports = () => {
const files = fs.readdirSync("./plugins")
var totalcount = 0
var successcount = 0
var failcount = 0
files.forEach((file) => {
if (file.endsWith(".plugin.js")){
try {
require("../../plugins/"+file)()
successcount++
totalcount++
}catch{
failcount++
totalcount++
}
}
})
log("info","loaded plugins",[{key:"success",value:successcount},{key:"error",value:failcount},{key:"total",value:totalcount}])
}
+24 -3
View File
@@ -41,7 +41,7 @@ exports.checker = async () => {
}
/**@param {String} value */
const checkToken = (value) => {
if (value.includes(" ") || value.length < 40 || value.length > 70){
if (value.includes(" ") || value.length < 40 || value.length > 90){
createError("'auth_token' | your token is invalid")
}
}
@@ -245,14 +245,13 @@ exports.checker = async () => {
//--------------------------|
//--------------------------|
var configArray = ["bot_name","main_color","server_id","auth_token","main_adminroles","prefix","languagefile","credits","status","system","options","messages"]
var configArray = ["main_color","server_id","auth_token","main_adminroles","prefix","languagefile","credits","status","system","options","messages"]
configArray.forEach((item) => {
if (config[item] == undefined){
throw new Error("\n\nMAIN ERROR: the item '"+item+"' doesn't exist in config.json")
}
})
checkType(config.bot_name,"string","bot_name")
checkHexColor(config.main_color,"main_color")
checkDiscord("serverid",config.server_id,"server_id")
checkToken(config.auth_token)
@@ -311,6 +310,28 @@ exports.checker = async () => {
})
//discord check
/**
const discord = require("discord.js")
const {GatewayIntentBits,Partials} = discord
const client = new discord.Client({
intents:[
GatewayIntentBits.DirectMessages,
GatewayIntentBits.GuildInvites,
GatewayIntentBits.GuildMembers,
GatewayIntentBits.GuildMessages,
GatewayIntentBits.Guilds,
GatewayIntentBits.MessageContent
],
partials:[Partials.Channel,Partials.Message]
})
await client.guilds.fetch()
if (!client.guilds.cache.find(g => g.id == config.server_id)){
createError("'server_id' | i'm not in a server with this id!")
}
*/
//the end
if (errorList.length > 0 || warnList.length > 0){
+4 -4
View File
@@ -167,7 +167,7 @@ module.exports = () => {
}
})
await require("./ticketCloser").closeTicket(interaction,prefix,"close")
await require("./ticketCloser").NEWcloseTicket(interaction.member,interaction.channel,prefix,"close")
closeTicketButtonChecker = false
})
@@ -218,7 +218,7 @@ module.exports = () => {
}
})
await require("./ticketCloser").closeTicket(interaction,prefix,"close")
await require("./ticketCloser").NEWcloseTicket(interaction.member,interaction.channel,prefix,"close")
closeTicket1ButtonChecker = false
})
@@ -270,7 +270,7 @@ module.exports = () => {
}
})
await require("./ticketCloser").closeTicket(interaction,prefix,"delete")
await require("./ticketCloser").NEWcloseTicket(interaction.member,interaction.channel,prefix,"delete")
deleteTicketButtonChecker = false
})
@@ -325,7 +325,7 @@ module.exports = () => {
}
})
await require("./ticketCloser").closeTicket(interaction,prefix,"deletenotranscript")
await require("./ticketCloser").NEWcloseTicket(interaction.member,interaction.channel,prefix,"deletenotranscript")
deleteTicket1ButtonChecker = false
})
}
+8 -8
View File
@@ -92,8 +92,8 @@ const normalLog = (debugString) => {
* @param {String} message
* @param {[{key:String,value:String}]} params
*/
exports.log = async (ptype,message,params) => {
var type = ptype
exports.log = async (type,message,params) => {
var ptype = type
const chalk = await loadChalk()
var paramstring = ""
if (params){
@@ -105,20 +105,20 @@ exports.log = async (ptype,message,params) => {
}
const parameters = params ? "("+paramstring+")" : " "
if (type == "command"){
if (ptype == "command"){
console.log(chalk.green("[command] ")+message+" "+chalk.yellow(parameters))
}else if (type == "info"){
}else if (ptype == "info"){
console.log(chalk.blue("[info] ")+message+" "+chalk.yellow(parameters))
}else if (type == "system"){
}else if (ptype == "system"){
console.log(chalk.green("[system] ")+message+" "+chalk.yellow(parameters))
}else if (type == "api"){
}else if (ptype == "api"){
if (require("./api/modules/base").enableApiLogs == true){
console.log(chalk.red("[api v"+require("./api/api.json").version+"] ")+message+" "+chalk.yellow(parameters))
}
type = "api v"+require("./api/api.json").version
ptype = "api v"+require("./api/api.json").version
}
const cd = new Date()
const months = ["January","February","March","April","May","June","July","August","September","October","November","December"]
normalLog("["+cd.getDate()+" "+months[cd.getMonth()-1]+" "+cd.getFullYear()+" - "+cd.getSeconds()+":"+cd.getMinutes()+":"+cd.getHours()+"] ["+type+"] "+message+" "+parameters)
normalLog("["+cd.getDate()+" "+months[cd.getMonth()-1]+" "+cd.getFullYear()+" - "+cd.getSeconds()+":"+cd.getMinutes()+":"+cd.getHours()+"] ["+ptype+"] "+message+" "+parameters)
}
+12
View File
@@ -6,6 +6,8 @@ const log = bot.errorLog.log
const l = bot.language
const storage = bot.storage
const APIEvents = require("./api/modules/events")
module.exports = async () => {
const chalk = await (await import("chalk")).default
@@ -34,23 +36,33 @@ module.exports = async () => {
interaction.guild.members.cache.find(u => u.id == user.id).roles.add(role)
log("system","added role (reaction roles)",[{key:"user",value:interaction.user.tag},{key:"role",value:role}])
const apirole = interaction.guild.roles.cache.find(r => r.id == role)
APIEvents.onReactionRole("add","add",apirole,interaction.user,interaction.channel,interaction.guild,new Date())
})
}else if (mode == "remove"){
option.roles.forEach((role) => {
interaction.guild.members.cache.find(u => u.id == user.id).roles.remove(role)
log("system","removed role (reaction roles)",[{key:"user",value:interaction.user.tag},{key:"role",value:role}])
const apirole = interaction.guild.roles.cache.find(r => r.id == role)
APIEvents.onReactionRole("remove","remove",apirole,interaction.user,interaction.channel,interaction.guild,new Date())
})
}else if (mode == "add&remove"){
option.roles.forEach((role) => {
if (interaction.guild.members.cache.find(u => u.id == user.id).roles.cache.has(role)){
interaction.guild.members.cache.find(u => u.id == user.id).roles.remove(role)
log("system","added role (reaction roles)",[{key:"user",value:interaction.user.tag},{key:"role",value:role}])
const apirole = interaction.guild.roles.cache.find(r => r.id == role)
APIEvents.onReactionRole("add","add&remove",apirole,interaction.user,interaction.channel,interaction.guild,new Date())
}else {
interaction.guild.members.cache.find(u => u.id == user.id).roles.add(role)
log("system","removed role (reaction roles)",[{key:"user",value:interaction.user.tag},{key:"role",value:role}])
const apirole = interaction.guild.roles.cache.find(r => r.id == role)
APIEvents.onReactionRole("remove","add&remove",apirole,interaction.user,interaction.channel,interaction.guild,new Date())
}
})
}
+144 -92
View File
@@ -5,37 +5,63 @@ const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const storage = bot.storage
const permsChecker = require("./utils/permisssionChecker")
exports.runThis = () => {
client.on("interactionCreate",async (interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "sendTranscript") return
interaction.deferUpdate()
/**
*
* @param {discord.Interaction} interaction
* @param {String} prefix
* @param {"delete"|"close"|"deletenotranscript"} mode
*/
exports.closeTicket = async (interaction,prefix,mode) => {
const chalk = await (await import("chalk")).default
const channelmessages = await interaction.channel.messages.fetch()
const channel = interaction.channel
channelmessages.sweep((msgSweep) => {
return msgSweep.author.id == client.user.id
})
/**
* @type {String} ticketuserarray
*/
const ticketuserarray = interaction.channel.name
const ticketusername = ticketuserarray.split(prefix)[1]
var fileattachment = await require("./transcript").createTranscript(channelmessages,interaction.channel)
var getuserID = storage.get("userTicketStorage",interaction.channel.id)
try {
var getusernameStep1 = client.users.cache.find(u => u.id === getuserID)
var isDatabaseError = false
}catch{
var isDatabaseError = true
if (fileattachment == false){
log("system","internal error: transcript is not created!")
interaction.channel.send({embeds:[bot.errorLog.serverError(l.errors.somethingWentWrongTranscript)]})
return
}
if (!getusernameStep1){
interaction.channel.send({content:"**"+l.messages.hereIsTheTranscript+"**",files:[fileattachment]})
})
}
/**
*
* @param {discord.GuildMember} member
* @param {discord.TextChannel} channel
* @param {String} prefix
* @param {"delete"|"close"|"deletenotranscript"} mode
*/
exports.NEWcloseTicket = async (member,channel,prefix,mode) => {
const guild = channel.guild
const user = member.user
const chalk = await (await import("chalk")).default
const channelmessages = await channel.messages.fetch()
//start code
//remove ot bot from transcript
channelmessages.sweep((msgSweep) => {return msgSweep.author.id == client.user.id})
/**@type {String}*/
const channelname = channel.name
const ticketOpenerChannelName = channelname.split(prefix)[1]
//get user that opened the ticket
var getuserID = storage.get("userTicketStorage",channel.id)
try {
var ticketOpener = client.users.cache.find(u => u.id === getuserID)
var isDatabaseError = false
}catch{var isDatabaseError = true}
if (!ticketOpener){
console.log(chalk.red("[database error]"),"something went wrong when getting the data in the database.\nNo panic, this error fixes itself!")
var isDatabaseError = true
}
@@ -44,22 +70,23 @@ exports.closeTicket = async (interaction,prefix,mode) => {
var deleteRequired = false
if (mode == "delete"){
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
try {
return interaction.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return interaction.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
//delete
//check perms
if (!guild) return
if (!permsChecker.command(user.id,guild.id)){
permsChecker.sendUserNoPerms(user)
return
}
//start delete proccess
deleteRequired = true
await interaction.channel.send({content:"**"+l.messages.gettingdeleted+"**"})
log("system","deleted a ticket",[{key:"user",value:interaction.user.tag},{key:"ticket",value:interaction.channel.name}])
await channel.send({content:"**"+l.messages.gettingdeleted+"**"})
log("system","deleted a ticket",[{key:"user",value:user.tag},{key:"ticket",value:channel.name}])
if (!isDatabaseError) storage.set("ticketStorage",getuserID,Number(storage.get("ticketStorage",getuserID)) - 1)
//getID & send DM
await interaction.channel.messages.fetchPinned().then(msglist => {
//getID & send DM & send api event
await channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return false
@@ -67,7 +94,7 @@ exports.closeTicket = async (interaction,prefix,mode) => {
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("./getoptions").getOptionsById("newT"+ticketId)
require("./api/modules/events").onTicketDelete(interaction.user,interaction.channel,interaction.guild,new Date(),{name:interaction.channel.name,status:"deleted",ticketOptions:ticketData})
require("./api/modules/events").onTicketDelete(user,channel,guild,new Date(),{name:channel.name,status:"deleted",ticketOptions:ticketData})
if (!firstmsg.embeds[0].author) return false
const id = firstmsg.embeds[0].author.name
@@ -76,42 +103,90 @@ exports.closeTicket = async (interaction,prefix,mode) => {
try{
if (config.system.enable_DM_Messages){
interaction.member.send({embeds:[bot.errorLog.custom(l.messages.deletedTicketDmTitle,l.messages.deletedTicketDmDescription,":ticket:",config.main_color)]})
member.send({embeds:[bot.errorLog.custom(l.messages.deletedTicketDmTitle,l.messages.deletedTicketDmDescription,":ticket:",config.main_color)]})
}
}
catch{log("system","can't send DM to member, member doesn't allow dm's")}
})
}else if (mode == "close"){
//close
//check perms
if (config.system.closeMode == "adminonly"){
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
try {
return interaction.member.send({embeds:[bot.errorLog.noPermsMessage]})
}catch{
return interaction.channel.send({embeds:[bot.errorLog.noPermsMessage]})
}
if (!guild) return
if (!permsChecker.command(user.id,guild.id)){
permsChecker.sendUserNoPerms(user)
return
}
}
//set new permissions
var permissionArray = []
const pfb = discord.PermissionFlagsBits
if (!isDatabaseError) permissionArray.push({
id:getusernameStep1,
id:ticketOpener,
type:"member",
allow:[pfb.ViewChannel],
deny:[pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages]
})
permissionArray.push({
id:interaction.guild.roles.everyone,
id:guild.roles.everyone,
type:"role",
deny:[pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel]
})
interaction.channel.permissionOverwrites.set(permissionArray)
//add main adminroles
config.main_adminroles.forEach((role,index) => {
try {
const adminrole = guild.roles.cache.find(r => r.id == role)
if (!adminrole) return
permissionArray.push({
id:adminrole,
type:"role",
allow:[pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel]
})
}catch{
log("system","invalid role! At 'config.json => main_adminroles:"+index)
}
})
//add ticket adminroles
await channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return false
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("./getoptions").getOptionsById("newT"+ticketId)
if (!ticketData) return
/**
* @type {String[]}
*/
const ticketadmin = ticketData.adminroles
ticketadmin.forEach((role,index) => {
if (!config.main_adminroles.includes(role)){
try {
const adminrole = guild.roles.cache.find(r => r.id == role)
if (!adminrole) return
permissionArray.push({
id:adminrole,
type:"role",
allow:[pfb.AddReactions,pfb.ViewChannel],
deny:[pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages]
})
}catch{
log("system","invalid role! At 'config.json => options/ticket/...:"+index)
}
}
})
})
channel.permissionOverwrites.set(permissionArray)
//message
var closeButtonRow = new discord.ActionRowBuilder()
@@ -144,20 +219,20 @@ exports.closeTicket = async (interaction,prefix,mode) => {
.setColor(config.main_color)
.setTitle(":lock: "+l.messages.closedTitle+" :lock:")
.setDescription(l.messages.closedDescription)
interaction.channel.send({embeds:[embed],components:[closeButtonRow]})
channel.send({embeds:[embed],components:[closeButtonRow]})
log("system","closed a ticket",[{key:"user",value:interaction.user.tag},{key:"ticket",value:interaction.channel.name}])
log("system","closed a ticket",[{key:"user",value:user.tag},{key:"ticket",value:channel.name}])
//getID & send DM
await interaction.channel.messages.fetchPinned().then(msglist => {
//getID & send DM & send api event
await channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return false
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("./getoptions").getOptionsById("newT"+ticketId)
require("./api/modules/events").onTicketClose(interaction.user,interaction.channel,interaction.guild,new Date(),{name:interaction.channel.name,status:"closed",ticketOptions:ticketData})
require("./api/modules/events").onTicketClose(user,channel,guild,new Date(),{name:channel.name,status:"closed",ticketOptions:ticketData})
const id = firstmsg.embeds[0].author.name
@@ -165,7 +240,7 @@ exports.closeTicket = async (interaction,prefix,mode) => {
try{
if (config.system.enable_DM_Messages){
interaction.member.send({embeds:[bot.errorLog.custom(l.messages.closedTicketDmTitle,l.messages.closedTicketDmDescription,":ticket:",config.main_color)]})
member.send({embeds:[bot.errorLog.custom(l.messages.closedTicketDmTitle,l.messages.closedTicketDmDescription,":ticket:",config.main_color)]})
}
}
catch{log("system","can't send DM to member, member doesn't allow dm's")}
@@ -173,22 +248,24 @@ exports.closeTicket = async (interaction,prefix,mode) => {
}else if (mode == "deletenotranscript"){
const permsmember = client.guilds.cache.find(g => g.id == interaction.guild.id).members.cache.find(m => m.id == interaction.member.id)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
interaction.channel.send({embeds:[bot.errorLog.noPermsMessage]})
//delete with no transcript
//check perms
if (!guild) return
if (!permsChecker.command(user.id,guild.id)){
permsChecker.sendUserNoPerms(user)
return
}
//start delete proccess
enableTranscript = false
deleteRequired = true
interaction.channel.send({content:"**"+l.messages.gettingdeleted+"**"})
log("system","deleted a ticket",[{key:"user",value:interaction.user.tag},{key:"ticket",value:interaction.channel.name}])
channel.send({content:"**"+l.messages.gettingdeleted+"**"})
log("system","deleted a ticket",[{key:"user",value:user.tag},{key:"ticket",value:channel.name}])
if (!isDatabaseError) storage.set("ticketStorage",getuserID,Number(storage.get("ticketStorage",getuserID)) - 1)
//getID & send DM
await interaction.channel.messages.fetchPinned().then(msglist => {
//getID & send DM & send api event
await channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return false
@@ -196,7 +273,7 @@ exports.closeTicket = async (interaction,prefix,mode) => {
const ticketId = firstmsg.embeds[0].footer.text.split("Ticket Type: ")[1]
const ticketData = require("./getoptions").getOptionsById("newT"+ticketId)
require("./api/modules/events").onTicketDelete(interaction.user,interaction.channel,interaction.guild,new Date(),{name:interaction.channel.name,status:"deleted",ticketOptions:ticketData})
require("./api/modules/events").onTicketDelete(user,channel,guild,new Date(),{name:channel.name,status:"deleted",ticketOptions:ticketData})
const id = firstmsg.embeds[0].author.name
@@ -204,7 +281,7 @@ exports.closeTicket = async (interaction,prefix,mode) => {
try{
if (config.system.enable_DM_Messages){
interaction.member.send({embeds:[bot.errorLog.custom(l.messages.deletedTicketDmTitle,l.messages.deletedTicketDmDescription,":ticket:",config.main_color)]})
member.send({embeds:[bot.errorLog.custom(l.messages.deletedTicketDmTitle,l.messages.deletedTicketDmDescription,":ticket:",config.main_color)]})
}
}
catch{log("system","can't send DM to member, member doesn't allow dm's")}
@@ -224,11 +301,11 @@ exports.closeTicket = async (interaction,prefix,mode) => {
const transcriptEmbed = new discord.EmbedBuilder()
.setColor(config.main_color)
.setTitle(l.messages.newTranscriptTitle)
.setAuthor({name:interaction.user.username,iconURL:interaction.user.displayAvatarURL({format:"png"})})
.setAuthor({name:user.username,iconURL:user.displayAvatarURL({format:"png"})})
.setDescription(l.messages.newTranscriptDescription)
.setFooter({text:"ticket: "+ticketuserarray})
.setFooter({text:"ticket: "+channelname})
interaction.guild.channels.cache.find(c => c.id == config.system.transcript_channel).send({
guild.channels.cache.find(c => c.id == config.system.transcript_channel).send({
embeds:[transcriptEmbed],
files:[fileattachment]
})
@@ -239,9 +316,9 @@ exports.closeTicket = async (interaction,prefix,mode) => {
.setColor(config.main_color)
.setTitle(l.messages.newTranscriptTitle)
.setDescription(l.messages.newTranscriptDescription)
.setFooter({text:"ticket: "+ticketuserarray})
.setFooter({text:"ticket: "+channelname})
if (!isDatabaseError) getusernameStep1.send({
if (!isDatabaseError) ticketOpener.send({
embeds:[transcriptEmbed],
files:[fileattachment]
})
@@ -253,31 +330,6 @@ exports.closeTicket = async (interaction,prefix,mode) => {
setTimeout(() => {resolve(true)},7000)
})}
await timer()
await interaction.channel.delete()
await channel.delete()
}
}
exports.runThis = () => {
client.on("interactionCreate",async (interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "sendTranscript") return
interaction.deferUpdate()
const channelmessages = await interaction.channel.messages.fetch()
channelmessages.sweep((msgSweep) => {
return msgSweep.author.id == client.user.id
})
var fileattachment = await require("./transcript").createTranscript(channelmessages,interaction.channel)
if (fileattachment == false){
log("system","internal error: transcript is not created!")
interaction.channel.send({embeds:[bot.errorLog.serverError(l.errors.somethingWentWrongTranscript)]})
return
}
interaction.channel.send({content:"**"+l.messages.hereIsTheTranscript+"**",files:[fileattachment]})
})
}
+6 -4
View File
@@ -33,11 +33,16 @@ exports.createEmbed = (id) => {
//-----------------------------------
//create the embed
const embed = new discord.EmbedBuilder()
.setColor(data.color)
.setTitle(data.name)
if (data.enableFooter) embed.setFooter({text:data.footer})
if (data.enableThumbnail) embed.setThumbnail(data.thumbnail)
if (data.enableCustomColor){
embed.setColor(data.color)
}else{
embed.setColor(config.main_color)
}
var description = data.description
if (data.enableTicketExplaination){
description = description+"\n\n__"+l.messages.chooseCategory+"__\n"
@@ -91,6 +96,3 @@ exports.createEmbed = (id) => {
const returnedData = {embed:embed,componentRows:componentRows}
return returnedData
}
this.createEmbed()
+77 -154
View File
@@ -92,160 +92,6 @@ module.exports = () => {
.setEmoji("🔓")
)
//NORMAL WAY
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicket") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenBar]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketFalse") return
interaction.deferUpdate()
interaction.message.edit({components:[closeRowClosed]})
})
const pfb = discord.PermissionFlagsBits
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketTrue") return
interaction.deferUpdate()
const embed = new discord.EmbedBuilder()
.setColor(config.main_color)
.setTitle(":unlock: "+l.messages.reopenTitle+" :unlock:")
.setDescription(l.messages.reopenDescription)
interaction.message.edit({embeds:[embed],components:[closeRowNormal]})
log("system","re-opened a ticket",[{key:"ticket",value:interaction.channel.name},{key:"user",value:interaction.user.tag}])
var permissionsArray = []
//set everyone allowed
if (config.system['has@everyoneaccess']){
var everyoneAllowPerms = [pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel]
var everyoneDenyPerms = []
}else{
var everyoneAllowPerms = []
var everyoneDenyPerms = [pfb.ViewChannel]
}
permissionsArray.push({
id:interaction.guild.roles.everyone,
type:"role",
allow:everyoneAllowPerms,
deny:everyoneDenyPerms
})
interaction.channel.permissionOverwrites.cache.forEach((p) => {
if (p.type == "member"){
permissionsArray.push({
id:p.id,
type:"member",
allow:[pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel],
deny:[]
})
}
})
interaction.channel.permissionOverwrites.set(permissionsArray)
})
//COMMAND WAY
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicket1") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenBar1]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketFalse1") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenCommandBar]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketTrue1") return
interaction.deferUpdate()
const embed = new discord.EmbedBuilder()
.setColor(config.main_color)
.setTitle(":unlock: "+l.messages.reopenTitle+" :unlock:")
.setDescription(l.messages.reopenDescription)
interaction.message.edit({content:null,embeds:[embed],components:[closeRowNormal]})
log("system","re-opened a ticket",[{key:"ticket",value:interaction.channel.name},{key:"user",value:interaction.user.tag}])
var permissionsArray = []
//set everyone allowed
if (config.system['has@everyoneaccess']){
var everyoneAllowPerms = [pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel]
var everyoneDenyPerms = []
}else{
var everyoneAllowPerms = []
var everyoneDenyPerms = [pfb.ViewChannel]
}
permissionsArray.push({
id:interaction.guild.roles.everyone,
type:"role",
allow:everyoneAllowPerms,
deny:everyoneDenyPerms
})
interaction.channel.permissionOverwrites.cache.forEach((p) => {
if (p.type == "member"){
permissionsArray.push({
id:p.id,
type:"member",
allow:[pfb.AddReactions,pfb.AttachFiles,pfb.EmbedLinks,pfb.SendMessages,pfb.ViewChannel],
deny:[]
})
}
})
interaction.channel.permissionOverwrites.set(permissionsArray)
//getID & send DM
interaction.channel.messages.fetchPinned().then(msglist => {
var firstmsg = msglist.last()
if (firstmsg == undefined || firstmsg.author.id != client.user.id) return false
const id = firstmsg.embeds[0].author.name
if (!id) return false
try{
if (config.system.enable_DM_Messages){
interaction.member.send({embeds:[bot.errorLog.custom(l.messages.reopenTicketDmTitle,l.messages.reopenTicketDmDescription,":ticket:",config.main_color)]})
}
}
catch{log("system","can't send DM to member, member doesn't allow dm's")}
})
})
//DASHBOARD (comming soon!)
/**
*
* @param {discord.Guild} guild
@@ -285,5 +131,82 @@ module.exports = () => {
})
channel.permissionOverwrites.set(permissionsArray)
require("./api/modules/events").onTicketReopen(user,channel,guild,new Date(),{name:channel.name,status:"reopened",ticketOptions:false})
}
//NORMAL WAY
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicket") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenBar]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketFalse") return
interaction.deferUpdate()
interaction.message.edit({components:[closeRowClosed]})
})
const pfb = discord.PermissionFlagsBits
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketTrue") return
interaction.deferUpdate()
const embed = new discord.EmbedBuilder()
.setColor(config.main_color)
.setTitle(":unlock: "+l.messages.reopenTitle+" :unlock:")
.setDescription(l.messages.reopenDescription)
interaction.message.edit({embeds:[embed],components:[closeRowNormal]})
reopenTicket(interaction.guild,interaction.channel,interaction.user)
})
//COMMAND WAY
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicket1") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenBar1]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketFalse1") return
interaction.deferUpdate()
interaction.message.edit({components:[reopenCommandBar]})
})
client.on("interactionCreate",(interaction) => {
if (!interaction.isButton()) return
if (interaction.customId != "reopenTicketTrue1") return
interaction.deferUpdate()
const embed = new discord.EmbedBuilder()
.setColor(config.main_color)
.setTitle(":unlock: "+l.messages.reopenTitle+" :unlock:")
.setDescription(l.messages.reopenDescription)
interaction.message.edit({content:null,embeds:[embed],components:[closeRowNormal]})
reopenTicket(interaction.guild,interaction.channel,interaction.user)
})
}
+4 -2
View File
@@ -44,6 +44,8 @@ const getUserInfo = (channel) => {
exports.createTranscript = async (messagecollection,channel) => {
const ticketuserdata = await getUserInfo(channel)
require("./api/modules/events").onTranscriptCreation(messagecollection,channel,channel.guild,new Date())
try {
const cd = new Date()
const months = ["January","February","March","April","May","June","July","August","September","October","November","December"]
@@ -57,8 +59,8 @@ exports.createTranscript = async (messagecollection,channel) => {
if (msg.content){var content = msg.content}else{var content = "*empty message*"}
const msgstats = "files: "+msg.attachments.size+" | embeds: "+msg.embeds.length+" | isbot: "+msg.author.bot
filearray.push("["+timestamp.getDate()+"/"+timestamp.getMonth()+"/"+timestamp.getFullYear()+" | "+timestamp.getHours()+":"+timestamp.getMinutes()+":"+timestamp.getSeconds()+" | "+msg.author.tag+" ] ["+msgstats+"]\n"+content+"\n")
const msgstats = "files: "+msg.attachments.size+", embeds: "+msg.embeds.length
filearray.push("["+timestamp.getDate()+"/"+timestamp.getMonth()+"/"+timestamp.getFullYear()+", "+timestamp.getHours()+":"+timestamp.getMinutes()+":"+timestamp.getSeconds()+"|"+msg.author.tag+"] ["+msgstats+"]\n"+content+"\n")
})
if (filearray.length < 2) filearray.push("transcript is empty")
+3
View File
@@ -0,0 +1,3 @@
/**
* @typedef {String|Boolean} OTErrorType
*/
+76
View File
@@ -0,0 +1,76 @@
const discord = require('discord.js')
const bot = require('../../index')
const client = bot.client
const config = bot.config
const log = bot.errorLog.log
const l = bot.language
const storage = bot.storage
/**
*
* @param {String} memberid
* @param {String} guildid
* @returns {Boolean} has permissions?
*/
exports.command = (memberid,guildid) => {
const permsmember = client.guilds.cache.find(g => g.id == guildid).members.cache.find(m => m.id == memberid)
if (config.main_adminroles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){
return false
}else {return true}
}
/**
*
* @param {discord.User} user
* @returns {Boolean}
*/
exports.sendUserNoPerms = (user) => {
try {
user.send({embeds:[bot.errorLog.noPermsMessage]})
return true
}catch{
return false
}
}
/**
*
* @param {discord.User} user
* @returns {Boolean}
*/
exports.sendUserNoTicket = (user) => {
try {
user.send({embeds:[bot.errorLog.notInATicket]})
return true
}catch{
return false
}
}
/**
*
* @param {discord.TextChannel} channel
* @returns {Boolean}
*/
exports.sendChannelNoPerms = (channel) => {
try {
channel.send({embeds:[bot.errorLog.noPermsMessage]})
return true
}catch{
return false
}
}
/**
*
* @param {discord.TextChannel} channel
* @returns {Boolean}
*/
exports.sendChannelNoTicket = (channel) => {
try {
channel.send({embeds:[bot.errorLog.notInATicket]})
return true
}catch{
return false
}
}
+7
View File
@@ -117,6 +117,9 @@ client.on('ready',async () => {
process.exit(1)
}
}
//load plugins
require("./core/api/pluginlauncher")()
})
if (!isDev){
@@ -148,6 +151,8 @@ if (process.argv[2] && process.argv[2].startsWith("slash")){
}
const APIEvents = require("./core/api/modules/events")
const debugLog = (debugString) => {
const content = fs.existsSync("./openticketdebug.txt") ? fs.readFileSync("./openticketdebug.txt").toString() : "==========================\n<OPEN TICKET DEBUG FILE:>\n=========================="
fs.writeFileSync("./openticketdebug.txt",content+"\nDEBUG: "+debugString)
@@ -169,6 +174,8 @@ process.on("uncaughtException",async (error,origin) => {
const chalk = await (await import("chalk")).default
console.log(chalk.red("\nOPEN TICKET ERROR: ")+error+"\n"+chalk.green("\nCreate a ticket in our support server for more information!\nIf you do this, you might help us to avoid a future bug!\n"))
errorLog(error.name+": "+error.message+" | origin: "+origin,error.stack)
APIEvents.onError(error.name+": "+error.message,new Date())
})
client.login(config.auth_token)
+79
View File
@@ -0,0 +1,79 @@
{
"errors":{
"missingArgsTitle":"Neplatné argumenty",
"missingArgsDescription":"Chybí argumenty",
"noPermsTitle":"Nemáš práva!",
"noPermsDescription":"Nemáš dostatečné práva na tento příkaz!\n Potřebuješ ADMINISTRATOR aby jsi mohl provést příkaz!",
"chooseFromListTitle":"Neplatné ID",
"chooseFromListDescription":"Vyber si z těchto ID:",
"boterror":"Error!",
"notInTicketTitle":"Nejsi v ticketu!",
"notInTicketDescription":"Tento příkaz nefunguje mimo tickety!",
"ticketDoesntExist":"Tento ticket už bohužel neexistuje!",
"roleDoesntExist":"Tato role bohužel neexistuje!",
"anotherOption":"Tato možnost není ticket ale něco jiného!",
"maxAmountTitle":"Maximální počet ticketů dosažen!",
"maxAmountDescription":"Dosáhl jsi maximálního povoleného počtu ticketů!\n Nemůžeš si vytvořit nový!",
"somethingWentWrong":"**Něco je špatně**\nProsím zkus to příště znovu!",
"somethingWentWrongTranscript":"Něco je špatně s transcriptem!**\nProsím zkus to příště znovu!"
},
"commands":{
"userAddedTitle":"Uživatel přidán!",
"userAddedDescription":"{0} je přidán do ticketu!",
"userRemovedTitle":"Uživatel odebrán!",
"userRemovedDescription":"{0} je odstraněn z ticketu!",
"renameTitle":"Jméno bylo změněno!",
"renameWarning":"Varování: jméno kanálu můžeš změnit pouze 2x za minutu!",
"closeTitle":"Zavři tento ticket!",
"closeDescription":"Můžeš zavřít ticket kliknutím na tlačítko níže!",
"deleteTitle":"Smaž tento ticket!",
"deleteDescription":"Můžeš smazat ticket kliknutím na tlačítko níže!",
"reopenTitle":"Znovu otevři ticket!",
"reopenDescription":"Můžeš znovu otevřít tento ticket kliknutínm na tlačítko níže!",
"ticketWarning":"The embed is in the message below!",
"maxTicketWarning":"**Varovaní:** _Můžeš si vytvořit použe {0} ticket(s) v jednu chvíli!_"
},
"helpMenu":{
"title":"Příkazy:",
"header1":"**Běž {0} vytvořit si ticket!**\n\n",
"header2":"**Použij příkaz `/new` nebo `/ticket` k vytvoření ticketu!**\n\n",
"msgCmd":"Vytvoř možnost otevírat tickety přes tlačítko. (ADMIN)",
"renameCmd":"Přejmenovat ticket. (Žádné mezery)",
"closeCmd":"Zavři ticket.",
"deleteCmd":"Smaž ticket.",
"addCmd":"Přidej člena do ticketu.",
"removeCmd":"Odebere člena z ticketu.",
"reopenCmd":"Znovu otevři ticket po uzavření."
},
"buttons":{
"close":"Zavři ticket",
"delete":"Smaž ticket",
"reopen":"Znovu otevři ticket",
"sendTranscript":"Odešli log ticketu"
},
"messages":{
"reopenTitle":"Ticket znovu otevřen!",
"reopenDescription":"Cítím se skvěle že si můžeme zase povídat!",
"closedTitle":"Zavřený ticket!",
"closedDescription":"Pouze admin team zde může nyní komunikovat!\n\n*Klikni na tlačítko níže pro smazání nebo znovu otevření ticketu!*",
"createdTitle":"Ticket vytvořen!",
"createdDescription":"Váš tiket je vytvořen, můžete ho zjistit pomocí pingu!",
"newTicketDmTitle":"Nový ticket!",
"closedTicketDmTitle":"Ticket uzavřen!",
"deletedTicketDmTitle":"Ticket smazán!",
"closedTicketDmDescription":"Tvůj ticket byl uzavřen!",
"deletedTicketDmDescription":"Tvůj ticket byl smazán!",
"reopenTicketDmTitle":"Ticket znovu otevřen!",
"reopenTicketDmDescription":"Tvůj ticket byl znovu otevřen!",
"newTranscriptTitle":"Nový log ticketu je zde!",
"newTranscriptDescription":"Zde najdeš log svého ticketu!",
"hereIsTheTranscript":"Zde je log:",
"chooseCategory":"Vyber kategorii:"
}
}
+2 -1
View File
@@ -1,6 +1,6 @@
{
"name": "open-ticket",
"version": "2.3.3",
"version": "2.4.0",
"description": "This is an open-source discord ticket bot, you can configure it and it comes with cool features like a transcript.",
"main": "index.js",
"scripts": {
@@ -13,6 +13,7 @@
"author": "DJdj Development",
"license": "ISC",
"dependencies": {
"axios": "^0.27.2",
"chalk": "^5.0.1",
"discord.js": "^14.0.2",
"express": "^4.17.1",
+22
View File
@@ -0,0 +1,22 @@
const discord = require("discord.js")
const api = require("../core/api/api.js")
module.exports = () => {
const {client,config,events,utils,actions} = api
//this code will run when the bot starts!
//in this example, we will say "hello" in the console when someone opens a ticket!
/**
events.onTicketOpen((user,channel,guild,date,ticketdata) => {
console.log("hello, someone opened a ticket!")
})
*/
}