Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
74 changes: 67 additions & 7 deletions RDMMonitor.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ const WEBSITE_AUTH = {
},
'jar': true
};
const wait = async ms => new Promise(done => setTimeout(done, ms));
var postingDelay = config.postingDelay * 60000;
var devices = {};
var instances = {};
Expand Down Expand Up @@ -113,11 +114,12 @@ bot.on('messageCreate', async message => {
if(member.roles.cache.has(AdminR.id)) {
if(command === "help") {
message.delete();
cmds = "`" + config.cmdPrefix + "restart` \\\u00BB to manually restart the whole bot.\n" +
"`" + config.cmdPrefix + "reopen <DEVICE-NAMES>` \\\u00BB to reopen the game on specific devices.\n" +
"`" + config.cmdPrefix + "reboot <DEVICE-NAMES>` \\\u00BB to reboot the specific devices.\n" +
"`" + config.cmdPrefix + "sam <DEVICE-NAMES>` \\\u00BB to reapply the SAM profile to the specific devices\n" +
"`" + config.cmdPrefix + "brightness <VALUE>, <DEVICE-NAMES>` \\\u00BB to change the brightness on the specific devices\n" +
var cmds = "`" + config.cmdPrefix + "restart` \\\u00BB to manually restart the whole bot.\n"
if(config.allowCMD) {cmds = cmds + "`" + config.cmdPrefix + "cmd <ALIAS>` \\\u00BB to execute a pre-defined command on the listening server.\n"}
if(config.allowReopenGame) {cmds = cmds + "`" + config.cmdPrefix + "reopen <DEVICE-NAMES>` \\\u00BB to reopen the game on specific devices.\n"}
if(config.allowWarnReboots) {cmds = cmds + "`" + config.cmdPrefix + "reboot <DEVICE-NAMES>` \\\u00BB to reboot the specific devices.\n"}
if(config.allowReapplySAM) {cmds = cmds + "`" + config.cmdPrefix + "sam <DEVICE-NAMES>` \\\u00BB to reapply the SAM profile to the specific devices\n"}
cmds = cmds + "`" + config.cmdPrefix + "brightness <VALUE>, <DEVICE-NAMES>` \\\u00BB to change the brightness on the specific devices\n" +
"The commands with `<DEVICE-NAMES>` accept multiple names separated by commas.\n" +
"They can be used to skip the exclusion list if you specify a name on the list.\n" +
"They can accept `all`, `allwarn`, or `alloff` to apply to groups but will omit devices on the exclude lists."
Expand All @@ -139,11 +141,17 @@ bot.on('messageCreate', async message => {
}
}

if(command === "cmd") {
CommandHandler(args)
return;
}

if(!args[0]) {
message.delete();
message.reply("Please enter a device name after the command like `" + config.cmdPrefix + "reboot 001-SE`");
return;
}

if(command === "brightness") {
let temp = parseInt(args[0]);
if (temp >= 0 && temp <= 100) {
Expand Down Expand Up @@ -873,7 +881,7 @@ function ReopenWarnGame(manDevices) {
console.info(GetTimestamp() + `Sending reopen game request for ${devices[reopenDevices[i]].name} to remote listener ${config.reopenMonitorURL[ii]}`);
if (manDevices) { bot.channels.cache.get(config.channel).send(`Sending reopen game request for ${devices[reopenDevices[i]].name} to remote listener`); }
request(options, (err, res, body) => {
if(err) {
if(err || body.status == 'error') {
console.error(GetTimestamp() + `Failed to send reopen game request to remote listener for ${options.body.device}`);
if (manDevices) { bot.channels.cache.get(config.channel).send(`Failed to send reopen game request to remote listener for ${options.body.device}`); }
}
Expand Down Expand Up @@ -941,7 +949,7 @@ function ReapplySAM(manDevices) {
console.info(GetTimestamp() + `Sending a request to reapply the SAM profile for ${devices[reapplyDevices[i]].name} to remote listener ${config.reapplySAMMonitorURL[ii]}`);
if (manDevices) { bot.channels.cache.get(config.channel).send(`Sending a request to reapply the SAM profile for ${devices[reapplyDevices[i]].name} to remote listener`); }
request(options, (err, res, body) => {
if(err) {
if(err || body.status == 'error') {
console.error(GetTimestamp() + `Failed to send request to reapply the SAM profile to remote listener for ${options.body.device}`);
if (manDevices) { bot.channels.cache.get(config.channel).send(`Failed to send request to reapply the SAM profile to remote listener for ${options.body.device}`); }
}
Expand Down Expand Up @@ -1727,6 +1735,58 @@ function GetIVQueue(instanceName) {
});
}

function CommandHandler(args) {
if(!config.allowCMD) {
return;
}
for(var ii = 0; ii < config.cmdMonitorURL.length; ii++) {
const options = {
url: config.cmdMonitorURL[ii],
json: true,
method: 'POST',
body: {
'type': 'cmd',
'cmdID': args[0]
},
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
};
console.info(GetTimestamp() + `Sending request to execute command \`${args[0]}\` to remote listener ${config.cmdMonitorURL[ii]}.`);
bot.channels.cache.get(config.channel).send(`Sending request to execute command ${args[0]} to remote listener ${config.cmdMonitorURL[ii]}.`);
request(options, async (err, res, body) => {
if(err) {
console.error(GetTimestamp() + `Failed to execute command \`${args[0]}\` on remote listener ${options.url}. Error: \n${err}`);
bot.channels.cache.get(config.channel).send(`Failed to execute command ${args[0]} on remote listener ${options.url}. Error: \n${err}`);
}
else if (body.status == 'error') {
console.error(GetTimestamp() + `Failed to execute command \`${args[0]}\` on remote listener ${body.node}. Error: \n${body.message}`);
bot.channels.cache.get(config.channel).send(`Failed to execute command ${args[0]} on remote listener ${body.node}. Error: \n${body.message}`);
}
else {
// Need to check that the character limit is maintained.
// Loop to create the message that is 2000 chars
// First has to include the starting text
// Send if the length is less than 2000
console.info(GetTimestamp() + `Message from ${body.node} at ${options.url}.`);
bot.channels.cache.get(config.channel).send(`Message from ${body.node} at ${options.url}.`);
if (body.message.length <= 2000) {
console.info(GetTimestamp() + body.message);
bot.channels.cache.get(config.channel).send(body.message);
}
else {
var m_array = body.message.match(/(.|[\r\n]){1,2000}/g);
for (i = 0; i < m_array.length; i++) {
console.info(GetTimestamp() + m_array[i]);
bot.channels.cache.get(config.channel).send(m_array[i]);
await wait(4000); // Wait 4 seconds between messages to be under the rate limit
}
}
}
});
}
}
process.on('uncaughtException', function(err) {
if(typeof err == 'object') {
err = JSON.stringify(err);
Expand Down
3 changes: 3 additions & 0 deletions RDMMonitorConfig.example.json
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,9 @@
"excludeFromReboots": ["Device01","Device02"],

"brightnessMonitorURL": ["http://192.168.0.1:6542","http://192.168.0.1:6543"],

"allowCMD": false,
"cmdMonitorURL": ["http://192.168.0.1:6542","http://192.168.0.1:6543"],

"cmdPrefix": ".",
"adminRoleName": "ADMIN-ROLE-NAME"
Expand Down
12 changes: 12 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,16 @@ RDMDeviceMonitor is a simple discord bot to monitor device status for RDM.
# SETTINGS
```
token: Mandator, discord bot token, bot should have send message and manage message permissions in the designated channel

channel: Default channel ID of where to post device/instance status
deviceStatusChannel: Specific channel ID of where to post device status
instanceStatusChannel: Specific channel ID of where to post instance status
deviceSummaryChannel: Specific channel ID of where to post the device summary
deviceDetailedSummaryChannel: Specific channel ID of where to post the device detailed summary
questChannel: Specific channel ID of where to post the quest instance details

userAlerts: an array of user IDs to DM upon device going offline

url: URL of your RDM website, by default IP:9000 but can use actual URL if you have a properly configured reverse proxy
websiteLogin: Username to login with
websitePassword: Password for the username
Expand All @@ -49,6 +53,8 @@ The above user must have admin access to the website
postIndividualDevices: true/false - Bool to post each device individually
postInstanceStatus: true/false - Bool to post instance status
postDeviceSummary: true/false - Bool to post device status in a single block by current status
postDeviceDetailedSummary: true/false - Bool to post device detailed status in a single block by current status
postQuestSummary: true/false - Bool to post quest instance status in a single block by current status

showInstance: Show which instance a device is assigned to on the individual device post
showAccount: Show account assigned on device post
Expand All @@ -61,6 +67,8 @@ clearMessagesOnStartup: Will delete all messages in the channel it is going to p

ignoredDevices: An array of strings for the overall device blacklist
ignoredInstances: An array of strings for the instance blacklist
ignoredQuestInstances: An array of strings for the quest instance blacklist

postingDelay: The time in minutes to delay different posting triggers

warningTime: The time in minutes to consider a device in warning state
Expand Down Expand Up @@ -88,6 +96,9 @@ excludeFromReboots: An array of strings that are the unique names of the devices

brightnessMonitorURL: An array of strings for the URLs of the brightness monitors you are using like iPhone Controller or DCM Listener

allowCMD: true/false - Bool to enable RDMDeviceMonitor to send a request to execute a predefined command on the monitor server
cmdMonitorURL: An array of strings for the URLs of the monitors you want to send command requests to

cmdPrefix: A single character used to identify commands that the bot should react to
adminRoleName: This is a string for the name of the main role that will admin the bot
```
Expand All @@ -110,6 +121,7 @@ Instead, add it to PM2 with `pm2 start ecosystem.config.js`
--`.reboot <DEVICE-NAMES>` » to reboot the specific devices<br>
--`.sam <DEVICE-NAMES>` » to reapply the SAM profile to the specific devices<br>
--`.brightness <VALUE>, <DEVICE-NAMES>` » to change the brightness on the specific devices<br>
--`.cmd <ALIAS>` » to execute a pre-defined command on the listening server<br>

The commands with `<DEVICE-NAMES>` accept multiple names separated by commas.<br>
They can be used to skip the exclusion list if you specify a name on the list.<br>
Expand Down