diff --git a/core/languageManager.js b/core/languageManager.js index a4ced7c..77d5e4f 100644 --- a/core/languageManager.js +++ b/core/languageManager.js @@ -4,7 +4,6 @@ if (index.developerConfig){ var config = require("../devconfig.json") }else{var config = require("../config.json")} - var localLanguage = require("../language/english.json") const fs = require("fs") const lfexists = fs.existsSync("./language/"+config.languageFile+".json") @@ -20,6 +19,12 @@ const successLog = async (language) => { const chalk = await (await import("chalk")).default require("./startscreen").headerDataLanguage("sucessfully loaded language "+language,false) + index.actionRecorder.push({ + category:"ot.managers.language", + file:"./core/languageManager.js", + time:new Date().getTime(), + type:"language.success" + }) } if (!localLanguage){ diff --git a/core/reactionRoles.js b/core/reactionRoles.js index fc8317a..6ce63b5 100644 --- a/core/reactionRoles.js +++ b/core/reactionRoles.js @@ -16,8 +16,12 @@ module.exports = async () => { if (interaction.isButton() && !interaction.customId.startsWith("newR")) return if (interaction.isStringSelectMenu() && !(interaction.customId == "OTdropdownMenu")) return - - + bot.actionRecorder.push({ + category:"ot.managers.reactionroles", + file:"./core/reactionRoles.js", + time:new Date().getTime(), + type:"reactionRoles.interactionCreated" + }) const optionidRaw = interaction.isStringSelectMenu() ? interaction.values[0] : interaction.customId @@ -40,6 +44,12 @@ module.exports = async () => { const user = interaction.member if (mode == "add"){ + bot.actionRecorder.push({ + category:"ot.managers.reactionroles", + file:"./core/reactionRoles.js", + time:new Date().getTime(), + type:"reactionRoles.type.add" + }) option.roles.forEach((role) => { interaction.guild.members.cache.find(u => u.id == user.id).roles.add(role) @@ -49,6 +59,12 @@ module.exports = async () => { }) }else if (mode == "remove"){ + bot.actionRecorder.push({ + category:"ot.managers.reactionroles", + file:"./core/reactionRoles.js", + time:new Date().getTime(), + type:"reactionRoles.type.remove" + }) option.roles.forEach((role) => { interaction.guild.members.cache.find(u => u.id == user.id).roles.remove(role) @@ -58,6 +74,12 @@ module.exports = async () => { }) }else if (mode == "add&remove"){ + bot.actionRecorder.push({ + category:"ot.managers.reactionroles", + file:"./core/reactionRoles.js", + time:new Date().getTime(), + type:"reactionRoles.type.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.add(role) diff --git a/core/utils/getButton.js b/core/utils/getButton.js index 86db8dc..36348a5 100644 --- a/core/utils/getButton.js +++ b/core/utils/getButton.js @@ -32,6 +32,12 @@ exports.getOption = getOption * @returns {discord.ButtonBuilder|false} */ exports.getButton = (id) => { + bot.actionRecorder.push({ + category:"ot.managers.utils", + file:"./core/utils/getButton.js", + time:new Date().getTime(), + type:"getbutton" + }) const option = getOption(id) if (!option) return false if (option.type == "ticket"){ @@ -67,28 +73,4 @@ exports.getButton = (id) => { } return button -} - - -exports.rawButtonData = class { - constructor() { - this.id = "" - this.name = "" - this.description = "" - this.icon = "" - this.label = "" - this.type = "" - - this.color = "" - this.enableDmOnOpen = true - this.url = "" - this.roles = ["",""] - this.mode = "" - this.adminroles = ["",""] - this.channelprefix = "" - this.category = "" - this.message = "" - this.ticketmessage = "" - - } } \ No newline at end of file diff --git a/core/utils/getDropdown.js b/core/utils/getDropdown.js index 130204b..04545dd 100644 --- a/core/utils/getDropdown.js +++ b/core/utils/getDropdown.js @@ -11,6 +11,12 @@ const configParser = require("./configParser") * @returns {discord.StringSelectMenuBuilder|false} */ exports.getDropdown = (ids,placeholder) => { + bot.actionRecorder.push({ + category:"ot.managers.utils", + file:"./core/utils/getDropdown.js", + time:new Date().getTime(), + type:"getdropdown" + }) const dropdown = new discord.StringSelectMenuBuilder() .setCustomId("OTdropdownMenu") .setDisabled(false) @@ -18,7 +24,7 @@ exports.getDropdown = (ids,placeholder) => { .setMinValues(1) .setPlaceholder(placeholder || l.messages.chooseATicket) .addOptions( - new discord.SelectMenuOptionBuilder() + new discord.StringSelectMenuBuilder() .setDefault(true) .setLabel(placeholder || l.messages.chooseATicket) .setValue("OTChooseTicket") @@ -28,7 +34,7 @@ exports.getDropdown = (ids,placeholder) => { const option = configParser.getTicketById(id,true) const roleoption = configParser.getRoleById(id,true) if (option){ - const selectComponent = new discord.SelectMenuOptionBuilder() + const selectComponent = new discord.StringSelectMenuOptionBuilder() .setDefault(false) .setValue("OTnewT"+option.id) @@ -43,7 +49,7 @@ exports.getDropdown = (ids,placeholder) => { dropdown.addOptions(selectComponent) }else if (roleoption){ - const selectComponent = new discord.SelectMenuOptionBuilder() + const selectComponent = new discord.StringSelectMenuOptionBuilder() .setDefault(false) .setValue("OTnewR"+roleoption.id) diff --git a/core/utils/getEmbed.js b/core/utils/getEmbed.js index 49324ab..f6a0f02 100644 --- a/core/utils/getEmbed.js +++ b/core/utils/getEmbed.js @@ -14,12 +14,18 @@ const l = bot.language exports.createEmbed = (id) => { + bot.actionRecorder.push({ + category:"ot.managers.utils", + file:"./core/utils/getEmbed.js", + time:new Date().getTime(), + type:"getembed" + }) //----------------------------------- //general importing const data = require("./configParser").getConfigMessage(id) /**@type {discord.ButtonBuilder[]}*/ var buttons = [] - /**@type {getButton.rawButtonData[]} */ + /**@type {import('./configParser').OTAllOptions[]} */ var buttonData = [] data.options.forEach((option) => { diff --git a/core/utils/liveStatus.js b/core/utils/liveStatus.js index 9bdd76d..4aa92ab 100644 --- a/core/utils/liveStatus.js +++ b/core/utils/liveStatus.js @@ -4,6 +4,7 @@ const client = bot.client const config = bot.config const log = bot.errorLog.log const axios = require("axios").default +const fs = require("fs") const loadChalk = async () => { return await (await import("chalk")).default @@ -15,6 +16,19 @@ const loadChalk = async () => { //OTLiveStatusError /**@typedef {{bot:{id:String,pfp:String,name:String}, openticket:{version:String,language:String, slashcmds:Boolean,transcripts:false|"text"|"html",config:{system:{},options:{},messages:{},transcripts:{}},plugins:String[],pluginload:{success:Number,error:Number,total:Number}}, details:{actions:[{type:String,category:String,file:String,time:Number}],errortime:Number}, error:String}} OTLiveStatusError */ +/**@type {[{type:String, category:String, file:String, time:Number}]} */ +exports.actionRecorder = [] + +//================================================================ +//=========================FUNCTIONS============================== +//================================================================ + +const getSlashEnabled = () => { + if (!fs.existsSync("./storage/slashcmdEnabled.txt")) return false + if (fs.readFileSync("./storage/slashcmdEnabled.txt").toString() == require("../../package.json").version){ + return true + }else return false +} /** * @param {Boolean} [local=false] @@ -68,8 +82,9 @@ exports.run = async (pluginData) => { var tsmode = bot.tsconfig.sendTranscripts.useHTMLtranscripts ? "html" : "text" const isTranscript = (a.transcripts.includes("html") && tsmode == "html" && tsenabled) || (a.transcripts.includes("text") && tsmode == "text" && tsenabled) || (a.transcripts.includes("both") && tsenabled) const isPlugins = (a.usingPlugins.includes("yes") && pluginData.total > 0) || (a.usingPlugins.includes("no") && pluginData.total == 0) || (a.usingPlugins.includes("both")) + const isSlashCMD = (a.usingSlashCommands.includes("yes") && getSlashEnabled()) || (a.usingSlashCommands.includes("no") && !getSlashEnabled()) || (a.usingSlashCommands.includes("both")) - if (!isLanguage || !isVersion || !isTranscript || !isPlugins) return + if (!isLanguage || !isVersion || !isTranscript || !isPlugins || !isSlashCMD) return announcement.style.forEach((s) => activeStyles.push(s)) }) const final = [] @@ -136,8 +151,43 @@ const uploadLiveStatus = (options) => { }) } -/**@param {String} err */ -const liveStatusUploadManager = (err) => { - //use globalPluginData for (some) plugin details +/**@param {String} err @returns {Promise}*/ +exports.liveStatusUploadManager = async (err) => { + return new Promise(async (resolve) => { + //use globalPluginData for (some) plugin details + var tsenabled = (bot.tsconfig.sendTranscripts.enableChannel || bot.tsconfig.sendTranscripts.enableDM) + var tsmode = bot.tsconfig.sendTranscripts.useHTMLtranscripts ? "html" : "text" + const transcriptMode = tsenabled ? tsmode : false + const slashMode = getSlashEnabled() + + try { + resolve(await uploadLiveStatus({ + bot:{ + id:client.user.id, + name:client.user.tag, + pfp:client.user.displayAvatarURL() + }, + error:err, + openticket:{ + config:{ + messages:config.messages, + options:config.options, + transcripts:bot.tsconfig, + system:config.system + }, + language:config.languageFile, + version:require("../../package.json").version, + slashcmds:slashMode, + transcripts:transcriptMode, + plugins:fs.readdirSync("./plugins"), + pluginload:globalPluginData + }, + details:{ + errortime:new Date().getTime(), + actions:this.actionRecorder + } + })) + }catch{resolve(false)} + }) } \ No newline at end of file diff --git a/core/utils/permisssionChecker.js b/core/utils/permisssionChecker.js index d75e69d..ab318fc 100644 --- a/core/utils/permisssionChecker.js +++ b/core/utils/permisssionChecker.js @@ -13,6 +13,12 @@ const storage = bot.storage * @returns {Boolean} has permissions? */ exports.command = (memberid,guildid) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"command" + }) const permsmember = client.guilds.cache.find(g => g.id == guildid).members.cache.find(m => m.id == memberid) if (config.adminRoles.some((item)=>{return permsmember.roles.cache.has(item)}) == false && !permsmember.permissions.has("Administrator") && !permsmember.permissions.has("ManageGuild")){ return false @@ -25,6 +31,12 @@ exports.command = (memberid,guildid) => { * @returns {Boolean} */ exports.sendUserNoPerms = (user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendusernoperms" + }) try { user.send({embeds:[bot.errorLog.noPermsMessage(user)]}) return true @@ -39,6 +51,12 @@ exports.sendUserNoPerms = (user) => { * @returns {Boolean} */ exports.sendUserNoTicket = (user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendusernoticket" + }) try { user.send({embeds:[bot.errorLog.notInATicket]}) return true @@ -53,6 +71,12 @@ exports.sendUserNoPerms = (user) => { * @returns {Boolean} */ exports.sendUserNoDelete = (user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendusernodelete" + }) try { user.send({embeds:[bot.errorLog.noPermsDelete(user)]}) return true @@ -68,6 +92,12 @@ exports.sendUserNoPerms = (user) => { * @returns {Boolean} */ exports.sendChannelNoPerms = (channel,user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendchannelnoperms" + }) try { channel.send({embeds:[bot.errorLog.noPermsMessage(user)]}) return true @@ -83,6 +113,12 @@ exports.sendUserNoPerms = (user) => { * @returns {Boolean} */ exports.sendChannelNoTicket = (channel,user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendchannelnoticket" + }) try { channel.send({embeds:[bot.errorLog.notInATicket]}) return true @@ -98,6 +134,12 @@ exports.sendUserNoPerms = (user) => { * @returns {Boolean} */ exports.sendChannelNoDelete = (channel,user) => { + bot.actionRecorder.push({ + category:"ot.managers.permissionChecker", + file:"./core/permissionChecker.js", + time:new Date().getTime(), + type:"sendchannelnodelete" + }) try { channel.send({embeds:[bot.errorLog.noPermsDelete(user)]}) return true diff --git a/index.js b/index.js index 119715a..9abfca5 100644 --- a/index.js +++ b/index.js @@ -75,10 +75,6 @@ if (process.argv.some((v) => v == "--devconfig")){ if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","loaded flags") exports.developerConfig = isDevConfig -const language = require("./core/languageManager").language -exports.language = language -if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","loaded language") - const config = tempconfig exports.config = config @@ -86,16 +82,21 @@ exports.config = config const tsconfig = isDevConfig ? require("./devtsconfig.json") : require("./transcriptconfig.json") exports.tsconfig = tsconfig +const language = require("./core/languageManager").language +exports.language = language +if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","loaded language") + if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","loaded config") exports.storage = require('./core/dynamicdatabase/storage') if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","loaded storage") exports.errorLog = require("./core/errorLogSystem") -const log = this.errorLog.log if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","LOADED LOGGING SYSTEM") if (process.argv.some((v) => v == "--debug")) console.log("[TEMP_DEBUG]","switching to new logs") this.errorLog.log("debug","loaded new logs") +exports.actionRecorder = require("./core/utils/liveStatus").actionRecorder + exports.hiddenData = require("./core/utils/hiddendata") this.errorLog.log("debug","loaded hiddendataTM") @@ -111,6 +112,12 @@ this.errorLog.log("debug","loaded buttons & embeds") client.on('ready',async () => { this.errorLog.log("debug","client logged in") + this.actionRecorder.push({ + category:"ot.managers.djs", + file:"index.js", + time:new Date().getTime(), + type:"client.loggedin.success" + }) var statusSet = false const setStatus = (type,text) => { if (statusSet == true) return @@ -124,10 +131,22 @@ client.on('ready',async () => { statusSet = true } this.errorLog.log("debug","bot status loaded") + this.actionRecorder.push({ + category:"ot.managers.djs", + file:"index.js", + time:new Date().getTime(), + type:"client.setstatus.success" + }) const chalk = await (await import("chalk")).default require("./core/startscreen").run() + this.actionRecorder.push({ + category:"ot.managers.main", + file:"index.js", + time:new Date().getTime(), + type:"startscreen.success" + }) if (!process.argv[2] || (process.argv[2] && !process.argv[2].startsWith("slash"))){ //normal start @@ -137,6 +156,13 @@ client.on('ready',async () => { setStatus(config.status.type,config.status.text) } + this.actionRecorder.push({ + category:"ot.managers.main", + file:"index.js", + time:new Date().getTime(), + type:"startmode.normal" + }) + var updatingSlash = false if (fs.existsSync("./storage/slashcmdEnabled.txt")){ /**@type {"true"|"false"|String} */ @@ -158,6 +184,12 @@ client.on('ready',async () => { updatingSlash = true } } + this.actionRecorder.push({ + category:"ot.managers.main", + file:"index.js", + time:new Date().getTime(), + type:"slashcmd.autoupdate.success" + }) try { await client.guilds.cache.find((g) => g.id == config.serverId).members.fetch() @@ -172,9 +204,21 @@ client.on('ready',async () => { this.errorLog.log("debug","slashmode activated") if (process.argv[3] == "enable"){ console.log(chalk.green("switching to slashEnable.js")) + this.actionRecorder.push({ + category:"ot.managers.main", + file:"index.js", + time:new Date().getTime(), + type:"startmode.slash.enable" + }) require("./core/slashSystem/slashEnable")() }else if (process.argv[3] == "disable"){ console.log(chalk.green("switching to slashDisable.js")) + this.actionRecorder.push({ + category:"ot.managers.main", + file:"index.js", + time:new Date().getTime(), + type:"startmode.slash.disable" + }) require("./core/slashSystem/slashDisable")() }else{ console.log(chalk.bgRed("[SLASH CMD MANAGER]: unknown slash command action!")) @@ -183,17 +227,49 @@ client.on('ready',async () => { } //load plugins + this.actionRecorder.push({ + category:"ot.managers.plugins", + file:"./core/api/pluginlauncher.js", + time:new Date().getTime(), + type:"plugins.loading" + }) require("./core/api/pluginlauncher")() + this.actionRecorder.push({ + category:"ot.managers.plugins", + file:"./core/api/pluginlauncher.js", + time:new Date().getTime(), + type:"plugins.success" + }) this.errorLog.log("debug","loading plugins") }) -if (!require("./core/api/api.json").disable.checkerjs.all) require("./core/checker").checker() +if (!require("./core/api/api.json").disable.checkerjs.all){ + this.actionRecorder.push({ + category:"ot.managers.main", + file:"./core/checker.js", + time:new Date().getTime(), + type:"checker.loading" + }) + require("./core/checker").checker() this.errorLog.log("debug","loading checker.js") this.errorLog.log("debug","checking config...") + this.actionRecorder.push({ + category:"ot.managers.main", + file:"./core/checker.js", + time:new Date().getTime(), + type:"checker.success" + }) +} if (process.argv[2] && process.argv[2].startsWith("slash")){ //do nothing }else{ + this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"commands.loading" + }) this.errorLog.log("debug","LOADING COMMANDS") //commands require('./commands/ticket')() @@ -207,7 +283,19 @@ if (process.argv[2] && process.argv[2].startsWith("slash")){ require("./commands/claim")() require("./commands/unclaim")() require("./commands/change")() + this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"commands.success" + }) + this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"core.loading" + }) this.errorLog.log("debug","LOADING CORE") //core require('./core/ticketActions/ticketOpener')() @@ -217,13 +305,38 @@ if (process.argv[2] && process.argv[2].startsWith("slash")){ //InteractionHandlers require("./core/interactionHandlers/handlers/handlers")() - //require("./test")() + this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"core.success" + }) } +this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"api.loading" +}) this.errorLog.log("debug","loading api") const APIEvents = require("./core/api/modules/events") const APIConfig = require("./core/api/api.json") +this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"api.success" +}) + +this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"debugsystem.loading" +}) + const debugLog = (debugString) => { if (!APIConfig.disable.debug.all && !APIConfig.disable.debug.debuglogs){ const content = fs.existsSync("./openticketdebug.txt") ? fs.readFileSync("./openticketdebug.txt").toString() : "==========================\n\n==========================" @@ -254,6 +367,16 @@ process.on("uncaughtException",async (error,origin) => { errorLog(error.name+": "+error.message+" | origin: "+origin,error.stack) APIEvents.onError(error.name+": "+error.message,new Date()) + + //TEMPORARY INTEGRATION FOR LIVESTATUS ERROR UPLOADER: + await require("./core/utils/liveStatus").liveStatusUploadManager(error.name+": "+error.message+" | origin: "+origin+"\n"+error.stack) +}) + +this.actionRecorder.push({ + category:"ot.managers.loader", + file:"./index.js", + time:new Date().getTime(), + type:"debugsystem.success" }) const token = config.token.fromENV ? process.env.TOKEN : config.token.value