This bot is based respectfully on the likeness of Lucretia Mott: https://en.wikipedia.org/wiki/Lucretia_Mott
All personality traits are purely fictional.
In order to develop locally for Lucretia:
-
Create a Test Server in Discord you intend to invite the Test Bot to.
-
Access the Discord Developer Portal. https://discord.com/developers/applications
-
Click "New Application" and give your test bot a name. You will be taken to the General Information panel for that Application.
-
Go to "Bot" in the sidebar. Click "Add A Bot", and approve the application as a bot.
-
Go to "OAuth2" in the sidebar. Under OAuth2 URL Generator > Scopes, click "bot" in the middle column.
-
Give Lucretia the Permissions in the Bot Permissions panel she needs to function. For a test server and a test account, it's ok to give her administrator access, but for the record, here are the permissions used by Lucretia in "production":
- General Permissions
- Manage Server
- Manage Roles
- Manage Channels
- Create Insant Invite
- Change Nickname
- Manage Nicknames
- Manage Emojis
- View Channels
- Text Permissions
- [ ALL ]
- Voice Permissions
- [ NONE ]
- General Permissions
-
Copy the Link provided in the Scopes panel and paste it into your browser, and invite + approve the bot to the Test Server you created earlier.
-
Okay! Now you have an Offline Test Bot in your Test Server. To get it online, you need to navigate to the Bot panel in Discord Developer Portal.
-
Under Build-A-Bot, click to reveal the token, the copy the token.
-
Create a .env file by typing this into your terminal from the root directory of your cloned repo:
touch .env -
Go into your new
.envfile and add this, replacing<your-token>with the token you copied:LOCAL=true DISCORD_TOKEN=<your-token>
-
If you do not have redis installed on your local machine, you will need to install and start a redis server:
brew install redis redis-server # to check redis connection, you may run: redis-cli ping # expected response if working: => PONG
-
When you're prepared, you may
npm installandnpm run watchinto your bash console at the root directory in order to launch the app in non-detatched local-dev mode. Congrats, your bot should now be online! You may debug and test with effervescence and beauty. Changes to the code will be automatically reloaded by nodemon, no need to start and stop the app (this is whatwatchis for). -
Add any new commands to the
helpcommand incommand-map.js. When making changes, please open a PR againstmasteron a branch and send to / tag Emma Hyde for approval and merge.
This bot uses the Eris.js framework in order to communicate with Discord (send messages, read messages, etc.)
Helpful Links:
- Primary Documentation:
- Eris: https://abal.moe/Eris/docs/getting-started
- Most Helpful Classes:
- Guild (This is the original word used by discord for Server): https://abal.moe/Eris/docs/Guild
- Message: https://abal.moe/Eris/docs/Message
- Channel: https://abal.moe/Eris/docs/Channel
- Member: https://abal.moe/Eris/docs/Member
- User: https://abal.moe/Eris/docs/User
- Role: https://abal.moe/Eris/docs/Role
- Most Helpful Classes:
- Redis: https://redis.io/documentation
- AsyncRedis (JS Client): https://openbase.io/js/async-redis/documentation
- Eris: https://abal.moe/Eris/docs/getting-started
When working to add a command in lib/command-map.js, the primary element we're working with is the message that triggered the command to fire. Let's use petkitty as an example, it is quite simple. When a member of a channel writes !petkitty, we enter the asynchronous execute function defined there.
{msg, args} =>
msg: Eris Message Object
args: Array[String] of message arguments
msg is the Eris Message Object. See Message documentation above for available functionality.
args is an Array of strings representing the passed parameters. This contains all of all words following the command petkitty, delimited by a space. If a message says !petkitty a b c, args will contain ['a', 'b', 'c'].
Just a few examples:
msg.channel- get the Eris::Channel Objectmsg.channel.id- get the channelID (useful for storing per-channel in redis)msg.guildID- get the serverIDmsg.author.mention- @Mentions the user who wrote the messagemsg.content- body of the message
If you want everything following the command to be one argument, you can do an args.join(' ').
If someone passes a Mention, you can get the user ID off of it with args[0].replace(/<@!(.*?)>/, (match, id) => id). This helps when associating the SAME user with whatever nickname they have at the time
Look through command-map.js for other examples.
Redis is a persisted in-memory data structure. It is great for when you're not storing anything particularly important or large (everything in this app) and is a lot smaller and easier to handle. In this app, it acts as a database. It can store strings, hashes, lists, sets, sorted sets with range queries, bitmaps, hyperloglogs, geospatial indexes with radius queries and streams. We use it for strings and hashes, and also probably lists.
We use Async Redis (library) to communicate with Redis.
In command-map.js, we use RedisClient to interact with it.
RedisClient.hset(<String> A, <String> B, <String> C): At hash named A, store key of B with value of C.RedisClient.hget(<String> A, <String> B): At hash named A, get value of key B.
The bash script that prepares the EC2 instance (installs node, etc.) is within the main.yml file.
AWS will pick up any and all changes of the actual JavaScript codebase, but unfortunately the current configuration will not pickup changes to the CloudFormation templates. In order to push changes to these stacks (including upgrading node), you need to run the deploy-infra.sh script in this directory after some enviornmental configuration:
- With an AWS account configured locally (use the AWS cli tool to configure your profiles), run:
This is a non-destructive way to ensure all are in existence.
mkdir -p ~/.env; touch ~/.env/lucretia-bott-access-token ~/.env/cli-profile - Enter each file and insert:
lucretia-bott-access-token: a Personal Access Token (created @ https://github.com/settings/tokens) that hasadmin:repo_hookandrepopermissions. You will need a personal access token for an account that has read + write access to the repository.cli-profile: this is the name of an aws profile configured through the aws cli tool (look for existing profiles at~/.aws/config&~/.aws/credentials) that has read + write access to the account running lucretia-bott.
- Once your bash environment is set up, we can run the bash script
bash deploy-infra.sh. It will print out the env variables it was able to derive from your environment. Note that if any of these are blank, something went wrong. - If there are errors, the AWS cli tool will walk you through them. If it says it was unable to find either of the above created files, make sure they contain only one string with the needed key or profile name, and ensure they're in the correct location.
You can watch the CloudFormation update occur at the CloudFormation/lucretia-bott and
CloudFormation/lucretia-bott-setup stacks. This is where you can see each resource get constructed and is
the likely location to find deploy resource failures.
CloudWatch is running for the app and setup scripts. You can see the logging for either at the CloudWatch page.