DEV Community

loading...

Get notified via Slack for new Chec orders

notrab profile image Jamie Barton ・5 min read

Following the announcement from Chec last week, webhooks are now available! I thought I'd take them for a spin and share a quick tutorial on creating an integration to get notified via Slack for new orders.

To do this, we will create a serverless function hosted on Zeit, listening to webhooks from Chec and messages sent to Slack using the @slack/webhook NPM package.

Slack notification

First things first

Chec
Chec (also known as Commerce.js) is an eCommerce API that boasts an excellent developer experience.

Zeit
We'll use Zeit to host our serverless function, and during development we can use the Now CLI to run our functions locally.

Slack
We'll be using Slack incoming webhooks to create our notification. You'll need to be logged into your admin area to configure the webhook.


Setup

First let's begin by creating our serverless function and local development with Now CLI.

Go ahead and create a new directory that you will deploy to Zeit Now.

mkdir slack-order-notification
cd slack-order-notification

It's also worth at this point linking the directory to Zeit Now.

now

The Now CLI will ask you which folder you want to link, to what account and any build instructions. All we need is to accept the defaults when asked.

Next, we'll install our dependencies.

yarn init -y # npm init -y
yarn add @slack/webhook # npm install @slack/webhook

Then create the following file api/slack-order-notification.js:

// api/slack-order-notification.js
module.exports = async (req, res) => {
  res.send('Hello world')
}

Now run now dev and you should that we're running on localhost:3000!

> Ready! Available at http://localhost:3000

You'll notice if you visit localhost:3000 in your browser that it will return a directory listing. This is normal.

Since we created the file at api/slack-order-notification.js, you can visit http://localhost:3000/api/slack-order-notification in your browser and you will see Hello world printed.


That's all! We have what we need to get started with building our Slack notification.

Slack Incoming Webhooks

You'll first need to setup a new Incoming WebHook via the Slack admin. Head to your workspace apps section and go to the Custom Integrations section.

For example, the URL to my workspace custom integrations is: https://launchmade.slack.com/apps/manage/custom-integrations. Once here, click on the Incoming WebHooks link and then Add to Slack.

  1. Pick a channel
  2. Click Add Incoming WebHooks integration
  3. Copy Webhook URL for later
  4. You can customize the name/icon if you desire

Next create a .env file in the root of your directory and add the following:

SLACK_ORDER_NOTIFICATION_WEBHOOK_URL=INSERT_WEBHOOK_URL_HERE

⚠️ Make sure to replace INSERT_WEBHOOK_URL_HERE with the Webhook URL you got from the steps above.

Send message to Slack

Now to test everything is working, let's update api/slack-order-notification.js to look a little something like:

const { IncomingWebhook } = require("@slack/webhook");

module.exports = async (req, res) => {
  const slack = new IncomingWebhook(
    process.env.SLACK_ORDER_NOTIFICATION_WEBHOOK_URL
  );

  const message = {
    text: "Hello world"
  };

  try {
    await slack.send(message);

    res.status(201).json({ sent: true });
  } catch (err) {
    res.status(400).json(err);
  }
};

Now if you visit http://localhost:3000/api/slack-order-notification in your browser, you should instantly be notified in Slack via the channel you configured to receive the incoming webhook.

Slack example message


Now all we've done here is instantiate a new Slack instance and sent a message in a format Slack is expecting.

Slack Building blocks

We'll be using the building blocks API from Slack to send rich messages. These messages can include formatted text, links, buttons and more.

We'll be creating something that looks a little something like:

Slack message

To achieve this we can use the block kit builder to create our fields.

We should end up with something like:

{
  "blocks":[
    {
      "type":"section",
      "text":{
        "type":"mrkdwn",
        "text":`You have a new order from *CUSTOMER_EMAIL*`
      },
      "fields":[
        {
          "type":"mrkdwn",
          "text":`*Customer reference:*\nCUSTOMER_REFERENCE`
        },
        {
          "type":"mrkdwn",
          "text":`*Sub total:*\nFORMATTED_ORDER_SUB_TOTAL`
        },
        {
          "type":"mrkdwn",
          "text":`*Items:*\nORDER_LINE_ITEMS_COUNT`
        }
      ]
    },
    {
      "type":"actions",
      "elements":[
        {
          "type":"button",
          "text":{
            "type":"plain_text",
            "text":"View order details"
          },
          "url":`https://dashboard.chec.io/orders/view/ORDER_ID`
        }
      ]
    }
  ]
}

If we go ahead and replace the variable message with the above, and revisit the endpoint, you will see an updated Slack message.

You'll also notice there are placeholders for:

  • CUSTOMER_EMAIL
  • CUSTOMER_REFERENCE
  • FORMATTED_ORDER_SUB_TOTAL
  • ORDER_LINE_ITEMS_COUNT

You could add more to the message, but this should be enough to illustrate the example we can send a notification to Slack with some key information.

Now you may be wondering where we get this information from, and that's where Chec webhooks come into it!

Chec webhooks

When a webhook is triggered, we will receive a payload object that contains everything we need to satisfy our variables above for the Slack notification.

Because our function is running locally on our machine in development, Chec has no way to trigger this endpoint. Thankfully we can use ngrok to tunnel the outside into our machine.

To do this, make sure you have ngrok installed, and now dev running, then type:

ngrok http 3000

Note: You will need to specify another PORT if Now is running on anything else but 3000.

Now let's configure a webhook that listens for the checkouts.capture event, and add the URL to our ngrok http URL, including our /api/slack-order-notification path and save.

Chec webhook configuration

Let's next destructure the payload object from req.body and use the applicable variables to populate our Slack blocks.

The updated function should look something like:

const { IncomingWebhook } = require("@slack/webhook");

module.exports = async (req, res) => {
  const slack = new IncomingWebhook(
    process.env.SLACK_ORDER_NOTIFICATION_WEBHOOK_URL
  );

  const { payload } = req.body;

  const message = {
    text: `New order from ${payload.customer.email}`,
    blocks: [
      {
        type: "section",
        text: {
          type: "mrkdwn",
          text: `You have a new order from *${payload.customer.email}*`
        },
        fields: [
          {
            type: "mrkdwn",
            text: `*Customer reference:*\n${payload.customer_reference}`
          },
          {
            type: "mrkdwn",
            text: `*Sub total:*\n${payload.order.subtotal.formatted_with_symbol}`
          },
          {
            type: "mrkdwn",
            text: `*Items:*\n${payload.order.line_items.length}`
          }
        ]
      },
      {
        type: "actions",
        elements: [
          {
            type: "button",
            text: {
              type: "plain_text",
              text: "View order details"
            },
            url: `https://dashboard.chec.io/orders/view/${payload.id}`
          }
        ]
      }
    ]
  };

  try {
    await slack.send(message);

    res.status(201).json({ sent: true });
  } catch (err) {
    res.status(400).json(err);
  }
};

Now if we save, and actually create an order with Chec, you will see an updated Slack message containing all the meta about your order!

Alt Text

Discussion (0)

pic
Editor guide