How to Send MongoDB Document Changes to a Slack Channel
In this tutorial, we will explore a seamless integration of your database with Slack using Atlas Triggers and the Slack API. Discover how to effortlessly send notifications to your desired Slack channels, effectively connecting the operations happening within your collections and relaying them in real-time updates.
The overall flow will be:
In this way, every time an operation that we need to trace is registered, the content of the transaction itself will be processed and used to send a message to a specific Slack channel.
Creating the application in Atlas
To begin with, we will create a new application in Atlas. A step-by-step guide illustrating this process is available in our documentation.
Once this has been completed, we are ready to start creating our first database trigger that will react every time there is an operation in a certain collection.
Atlas trigger
For this tutorial, we will create a trigger that monitors all changes in a test collection for insert, update, and delete operations.
To create a new database trigger, you will need to:
Please note that this trigger will make use of the event ordering as we want the operations to be processed according to when they were performed.
The trigger configuration values will look like this:
Finally, this trigger will be linked to a processEvent function which we'll see below.
Atlas functions
To create an Atlas function using the UI, we need to:
"processEvent" function
The processEvent function will process the change events every time an operation we are monitoring in the given collection is processed. In this way, we are going to create an object that we will then send to the function in charge of sending this message in Slack.
The code of the function is the following:
exports = function(changeEvent) {
const docId = changeEvent.documentKey._id;
const { updateDescription, operationType } = changeEvent;
var object = {
operationType,
docId,
};
if (updateDescription) {
const updatedFields = updateDescription.updatedFields; // A document containing updated fields
const removedFields = updateDescription.removedFields; // An array of removed fields
object = {
...object,
updatedFields,
removedFields
};
}
const result = context.functions.execute("sendToSlack", object);
return true;
};
In this function, we will create an object that we will then send as a parameter to another function that will be in charge of sending to our Slack channel.
Here we will use change event and its properties to capture the:
With all this, we create an object and make use of the internal function calls to execute our sendToSlack function.
Recommended by LinkedIn
"sendToSlack" function
This function will make use of the "chat.postMessage" method of the Slack API to send a message to a specific channel.
To use the Slack library, you must add it as a dependency in your Atlas function. Therefore, in the Functions section, we must go to the Dependencies tab and install @slack/web-api.
You will need to have a Slack token that will be used for creating the WebClient object as well as a Slack application. Therefore:
A full guide on how to get these two can be found in the Quickstart guide for the next-generation Slack platform.
First, we will perform the logic with the received object to create a message adapted to the event that occurred.
var message = "";
if (arg.operationType == 'insert') {
message += `A new document with id \`${arg.docId}\` has been inserted`;
} else if (arg.operationType == 'update') {
message += `The document \`${arg.docId}\` has been updated.`;
if (arg.updatedFields && Object.keys(arg.updatedFields).length > 0) {
message += ` The fileds ${JSON.stringify(arg.updatedFields)} has been modified.`;
}
if (arg.removedFields && arg.removedFields.length > 0) {
message += ` The fileds ${JSON.stringify(arg.removedFields)} has been removed.`;
}
} else {
message += `An unexpected operation affecting document \`${arg.docId}\` ocurred`;
}
Once we have the library, we must use it to create a WebClient client that we will use later to make use of the methods we need.
const { WebClient } = require('@slack/web-api');
// Read a token from the environment variables
const token = context.values.get('SLACK_TOKEN');
// Initialize
const app = new WebClient(token);
Finally, we can send our message with:
try {
// Call the chat.postMessage method using the WebClient
const result = await app.chat.postMessage({
channel: channelId,
text: `New Event: ${message}`
});
console.log(result);
}
catch (error) {
console.error(error);
}
The full function code will be as:
exports = async function(arg){
const { WebClient } = require('@slack/web-api');
// Read a token from the environment variables
const token = context.values.get('SLACK_TOKEN');
const channelId = context.values.get('CHANNEL_ID');
// Initialize
const app = new WebClient(token);
var message = "";
if (arg.operationType == 'insert') {
message += `A new document with id \`${arg.docId}\` has been inserted`;
} else if (arg.operationType == 'update') {
message += `The document \`${arg.docId}\` has been updated.`;
if (arg.updatedFields && Object.keys(arg.updatedFields).length > 0) {
message += ` The fileds ${JSON.stringify(arg.updatedFields)} has been modified.`;
}
if (arg.removedFields && arg.removedFields.length > 0) {
message += ` The fileds ${JSON.stringify(arg.removedFields)} has been removed.`;
}
} else {
message += `An unexpected operation affecting document \`${arg.docId}\` ocurred`;
}
try {
// Call the chat.postMessage method using the WebClient
const result = await app.chat.postMessage({
channel: channelId,
text: `New Event: ${message}`
});
console.log(result);
}
catch (error) {
console.error(error);
}
};
Note: The bot token we use must have the minimum permissions to send messages to a certain channel. We must also have the application created in Slack added to the channel where we want to receive the messages.
If everything is properly configured, every change in the collection and monitored operations will be received in the Slack channel:
Please note that this example here is a simple guide. But from this guide, it can be extended and adapted to more complex needs.
You can use $match" expressions to only detect certain changes and then adapt the change event to only receive certain fields with a "$project".
Conclusion
In this tutorial, we've learned how to seamlessly integrate your database with Slack using Atlas Triggers and the Slack API. This integration allows you to send real-time notifications to your Slack channels, keeping your team informed about important operations within your database collections.
We started by creating a new application in Atlas and then set up a database trigger that reacts to specific collection operations. We explored the processEvent function, which processes change events and prepares the data for Slack notifications. Through a step-by-step process, we demonstrated how to create a message and use the Slack API to post it to a specific channel.
Now that you've grasped the basics, it's time to take your integration skills to the next level. Here are some steps you can follow:
By taking these steps, you'll be well on your way to creating powerful, customized integrations that can streamline your workflow and keep your team in the loop with real-time updates. Good luck with your integration journey!