A friendly Discord bot for a Minecraft server

Commands

The famous !on command

This command has been created somehow randomly as an unforeseen but welcomed feature of a custom player-tracking system. It is an extremely rare feature for unaltered, vanilla Bedrock servers directly from Mojang and it is achieved by the scripted interaction with the server’s console. This is only possible on totally custom set-ups Ig.

!on command returns Gamer Tags of players currently on-line in Mincraft and shows whether they have the Emerald tag.
It also tells some OS stats such as CPU, memory usage and time since reboot. The OS stats image is created on-the-fly with Canvas.js

Other commands

From a simple !hi which triggers a random text response to more advanced commands such as !whitelist or !playtime which receive data either from server’s console or MySQL database, Sharon can do it all in a casual manner that resonates well with young audience.

!playtime pulls data from MySQL database and presents in a digestive form.
The !whitelist command is available only in designated channels with limited access.
Sharon throws a random message to give the user initial feedback as the !whitelist command takes some time to complete.
The bot also informs a user that they have been whitelisted and provides further instructions.

The bot has many more commands and they keep evolving in response to users interaction. Since this is just single-server thing I can update it whenever I please without following any particular release patterns. That gives room for experimentation.

The code

Discord’s API as well written and easy to learn. Below there is an example of simple command’s code.

module.exports =
   name: 'ping'
   description: 'Ping!'
   cooldown: .3
   execute: (client, config, message, args) ->
      message.channel.send 'Pong.'
         .catch (error) -> client.helpers.error_message_send error, {command: @.name}; return
      return
The !on command joins couple of txt files that are created by a lunchd task running on the MC Server’s machine. It does so in a rather crude way at the moment. One could say that a fox is being helped by cat.

Below there is an excerpt from my sought-after !whitelist command. Whitelisting in vanilla Bedrock can only be performed via command-line and can be a pain in the neck for server owners.

# [...]

               send = 'whitelist add "' + gtag + '"'
               expect = '"Player already in whitelist*" "Failed*" "No targets*"' # the array of expected strings sending as space separated quoted strings

            else if subcommand == 'remove'
               send = 'whitelist remove "' + gtag + '"'
               expect = '"Player removed from whitelist*" "Player not in whitelist*"'

            message.channel.send client.helpers.random([ 'okay, lemme see', 'oof, back to work', 'communicating with MC server', 'talking to Minecraft Gods', 'sure, why not']) + " ...⏳"
               .catch (error) -> client.helpers.error_message_send error, err_msg_send_args; return

            client.libs.exec config.abspath + '/mc-connect/mc-connect.exp.sh \'' + send + '\' \'' + expect + '\'', (error, stdout, stderr) ->
               if error
                  console.log 'error: ' + error.message
                  message.channel.send "Wasn't able to do the whitelist thingy this time.\rYou can always try again #{message.author} ..."
                     .catch (error) -> client.helpers.error_message_send error, err_msg_send_args; return
                  return
               if stderr
                  console.log 'stderr: ' + stderr
                  message.channel.send "Wasn't able to do the whitelist thingy this time.\rYou can always try again #{message.author} ..."
                     .catch (error) -> client.helpers.error_message_send error, err_msg_send_args; return
                  return

               # handle responses from the expect script
               # ---- add
               if stdout.includes('Player added to whitelist’)
# [...]

The corresponding except code follows

#!/usr/bin/expect --

log_user 0

# log_file /var/sharon_log.log
set timeout 5
spawn ssh “*********"
expect "*$ "

# set the prompt to a known value
#send "PS1='>'\r"
#expect -re {>$}

send "docker attach --detach-keys=Q emer\r"
expect "DEBU*"

log_user 1
send "[lindex $argv 0]\r"
foreach arg [lindex $argv 1] {
  expect "$arg"
}

log_user 0

send "Q"
# expect ">$"
expect "*$ "


send "exit\r"
expect eof

exit

Historical context

Discord is a worthy successor of hum radio and IRC. This robust, highly customisable platform offers some unique, useful features which the mainstream social media and communication apps lack.

Apart from plethora of free and commercial bots available for Discord the Node-powered Discord.js library offers clear API making it easy to create and deploy your own bots. Psst, it is also available in Python.

As it happens I do own a little Minecraft Bedrock server running on a spare MacMini. Mincraft servers cannot exist without Discord these days and a Discord server without bots, therfore Sharon was born.

Conclusion

You can significantly improve the experience of your own Minecraft server by developing a custom Discord bot. It is also a fun way of learning JavaScript, Node.js / Python, Bash, Expect and various other geeky command-line & dev tools.

Discord.js Guide


If you play Emerland I’m giving you a diamond block for finding this post lol :D

Disclaimer

My bot doesn’t have anything in common with a COVID-19 troll-bot with the same name.

You may also like…

Add a comment