Skip to content
18 changes: 18 additions & 0 deletions .circleci/test-deploy.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,24 @@ jobs:
template: basic_success_1
event: always
thread_id: orb-testing-thread-<${CIRCLE_SHA1}>
- slack/notify:
debug: true
step_name: "Message with thread updated"
event: always
update_notification: true
thread_id: orb-testing-thread-<${CIRCLE_SHA1}>
custom: |
{
"blocks": [
{
"type": "section",
"text": {
"type": "mrkdwn",
"text": "This message should be on thread and updating thread"
}
}
]
}
- slack/notify:
debug: true
step_name: "Custom template with group mention"
Expand Down
25 changes: 25 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,31 @@ Post replies in threads with a special parameter `thread_id`. Including this par
}
```

## Update Top Level Messages

Update a top level message using the `thread_id` parameter. Can update the top of a threaded message or a standalone message. include the parameter `update_notification: true` to specify that this will be an update of an existing message. If the `thread_id` is missing or not found, the message will be posted as a new message instead.

```yaml
- slack/notify:
event: always
update_notification: true
custom: |
{
"blocks": [
{
"type": "section",
"fields": [
{
"type": "plain_text",
"text": "*This is a text notification*",
"emoji": true
}
]
}
]
}
```

## Scheduled Message

Set the `scheduled_offset_seconds` special parameter to a number of seconds if you want to post a scheduled message. Example:
Expand Down
5 changes: 5 additions & 0 deletions src/commands/notify.yml
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,10 @@ parameters:
default: 0
description: |
When set, the notification is a scheduled message.
update_notification:
type: boolean
default: false
description: When set, the parent notification of the thread is updated
retries:
type: integer
default: 0
Expand Down Expand Up @@ -142,6 +146,7 @@ steps:
SLACK_PARAM_THREAD: "<<parameters.thread_id>>"
SLACK_PARAM_OFFSET: "<<parameters.scheduled_offset_seconds>>"
SLACK_SCRIPT_NOTIFY: "<<include(scripts/notify.sh)>>"
SLACK_PARAM_UPDATE: "<<parameters.update_notification>>"
SLACK_SCRIPT_UTILS: "<<include(scripts/utils.sh)>>"
# import pre-built templates using the orb-pack local script include.
basic_fail_1: "<<include(message_templates/basic_fail_1.json)>>"
Expand Down
102 changes: 102 additions & 0 deletions src/examples/update_notification.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
description: |
Send a Slack notification to a channel and use the same message to post replies in a thread.
`thread_id` parameter holds a thread identifier in case there are multiple notifications in the pipeline
usage:
version: 2.1
orbs:
slack: circleci/slack@5.0
node: circleci/node:4.1
jobs:
test:
executor:
name: node/default
steps:
- slack/notify:
event: always
channel: engineering
thread_id: testing
custom: |
{
"blocks": [
{
"type": "section",
"fields": [
{
"type": "plain_text",
"text": "*Tests started.*",
"emoji": true
}
]
}
]
}
- slack/notify:
event: always
channel: engineering
thread_id: testing
update_notification: true
custom: |
{
"blocks": [
{
"type": "section",
"fields": [
{
"type": "plain_text",
"text": "*Tests finished.*",
"emoji": true
}
]
}
]
}
deploy:
executor:
name: node/default
steps:
- slack/notify:
event: always
channel: engineering
thread_id: deployment
custom: |
{
"blocks": [
{
"type": "section",
"fields": [
{
"type": "plain_text",
"text": "*Deployment started.*",
"emoji": true
}
]
}
]
}
- slack/notify:
event: always
channel: engineering
thread_id: deployment
update_notification: true
custom: |
{
"blocks": [
{
"type": "section",
"fields": [
{
"type": "plain_text",
"text": "*Deployment finished.*",
"emoji": true
}
]
}
]
}
workflows:
deploy_and_notify:
jobs:
- deploy
- test:
requires:
- deploy
16 changes: 13 additions & 3 deletions src/scripts/notify.sh
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ NotifyWithRetries() {
local success_request=false
local retry_count=0
while [ "$retry_count" -le "$SLACK_PARAM_RETRIES" ]; do
if SLACK_SENT_RESPONSE=$(curl -s -f -X POST -H 'Content-type: application/json' -H "Authorization: Bearer $SLACK_ACCESS_TOKEN" --data "$SLACK_MSG_BODY" "$1"); then
if SLACK_SENT_RESPONSE=$(curl -s -f -X POST -H 'Content-type: application/json; charset=utf-8' -H "Authorization: Bearer $SLACK_ACCESS_TOKEN" --data "$SLACK_MSG_BODY" "$1"); then
echo "Notification sent"
success_request=true
break
Expand Down Expand Up @@ -101,8 +101,15 @@ PostToSlack() {
# get the value of the specified thread from the environment
# SLACK_THREAD_TS=12345.12345
SLACK_THREAD_TS=$(eval "echo \"\$$SLACK_PARAM_THREAD\"")
# append the thread_ts to the body for posting the message in the correct thread
SLACK_MSG_BODY=$(echo "$SLACK_MSG_BODY" | jq --arg thread_ts "$SLACK_THREAD_TS" '.thread_ts = $thread_ts')
if [ "$SLACK_PARAM_UPDATE" ]; then
# when updating, the key ts is used to reference the message to be updated
TS=$(eval "echo \"\$$SLACK_PARAM_THREAD\"")
SLACK_MSG_BODY=$(echo "$SLACK_MSG_BODY" | jq --arg ts "$TS" '.ts = $ts')
SLACK_UPDATE=true
else
# append the thread_ts to the body for posting the message in the correct thread
SLACK_MSG_BODY=$(echo "$SLACK_MSG_BODY" | jq --arg thread_ts "$SLACK_THREAD_TS" '.thread_ts = $thread_ts')
fi
fi

echo "Sending to Slack Channel: $i"
Expand All @@ -127,7 +134,10 @@ PostToSlack() {
SLACK_MSG_BODY=$(echo "$SLACK_MSG_BODY" | jq --arg post_at "$POST_AT" '.post_at = ($post_at|tonumber)')
# text is required for scheduled messages
SLACK_MSG_BODY=$(echo "$SLACK_MSG_BODY" | jq '.text = "Dummy fallback text"')

NotifyWithRetries https://slack.com/api/chat.scheduleMessage
elif [ $SLACK_UPDATE ]; then
NotifyWithRetries https://slack.com/api/chat.update
else
NotifyWithRetries https://slack.com/api/chat.postMessage
fi
Expand Down