Schedule Slack messages and daily digests

Post to any Slack channel on a schedule: a standup digest, a reminder, a daily number, or an announcement. cronservices sends the message through an incoming webhook, so there's no bot to host, and it can fill the message in from any API first.

Example: a daily Slack reminder

The simplest job: a message every weekday at 09:30 in your time zone.

json
{
  "name": "Standup reminder",
  "cron": { "expression": "30 9 * * 1-5", "time_zone": "America/New_York" },
  "nodes": [
    { "id": "post", "slack_send_message": {
        "webhook_url": "https://hooks.slack.com/services/T000/B000/XXXX",
        "text": ":wave: Standup in 15 minutes. Post your update in the thread." } }
  ]
}

Example: open pull requests before standup

Fetch data, turn it into lines, and post it. The join function writes a list as text, one item per line:

json
{
  "name": "Open PRs to #eng",
  "cron": { "expression": "0 9 * * 1-5", "time_zone": "Europe/Berlin" },
  "nodes": [
    { "id": "prs", "github_list_pull_requests": { "credential_id": "YOUR_GITHUB_CREDENTIAL_ID", "owner": "acme", "repo": "web", "state": "open" } },
    { "id": "lines", "transform": { "template": "{ \"count\": \"{{ $.length }}\", \"lines\": { \"{{#each $}}\": \"• <{{ $.html_url }}|#{{ $.number }}> {{ $.title }}\" } }" } },
    { "id": "post", "slack_send_message": {
        "webhook_url": "https://hooks.slack.com/services/T000/B000/XXXX",
        "text": "*{{ $.count }} open pull requests*\n{{ join($.lines, \"\\n\") }}" } }
  ]
}

Set up

  1. Create a Slack app at api.slack.com/apps, turn on Incoming Webhooks, and add a webhook to the channel.
  2. Copy the https://hooks.slack.com/services/… URL into webhook_url. Treat it as a secret: anyone with it can post to the channel.
  3. To read messages with slack_channel_history, give the app a bot token with channels:history and save it as a bearer_token credential.

To send Slack's richer Block Kit layouts, use a request step that posts your own blocks JSON to the same webhook.

Reference

Send a Slack message: slack_send_message

Sends POST to the incoming webhook URL with {"text": …}. Output for the next step: The text ok.

Field Type Notes
webhook_url string, required An incoming webhook URL, https://hooks.slack.com/services/…, from a Slack app with Incoming Webhooks turned on.
text string, required Slack mrkdwn: *bold*, _italic_, <https://example.com|a link>. Up to 40,000 characters. Placeholders allowed.

Read a Slack channel: slack_channel_history

Sends GET https://slack.com/api/conversations.history. Output for the next step: Slack's response: messages (newest first), each with text, user and ts.

Field Type Notes
credential_id string, required The id of a bearer_token credential holding a bot token (xoxb-…) with channels:history, groups:history or im:history.
channel string, required A channel, private group or DM id, such as C0123456789.
limit integer 1 to 100. Omit for Slack’s default of 100.

More ideas

  • Post yesterday's signups from your analytics API every morning: 0 8 * * *.
  • Announce who's on call from PagerDuty: 0 9 * * MON.
  • Post past-due Stripe subscriptions each weekday.
  • Remind the team about timesheets on the last weekday of the month: 0 15 LW * *.
  • Post a weather brief for a field crew at 05:30 local time.