Slack
Post to a Slack channel using either an incoming webhook (no SDK needed) or the Web API with @slack/web-api. The webhook flow is shown below.
Channel setup
- Create a Slack app and enable Incoming Webhooks.
- Add a new webhook for the target channel and copy the URL.
- Set
SLACK_WEBHOOK_URLin your.env.
Define the effect
src/effects/slack.ts
import { createEffect, S } from "envio";
export const sendSlack = createEffect(
{
name: "sendSlack",
input: {
text: S.string,
blocksJson: S.optional(S.string), // JSON-encoded Block Kit array
},
rateLimit: { calls: 1, per: "second" }, // Slack: ~1 msg/sec/channel
mode: "orderedAfterCommit",
},
async ({ input, context }) => {
const res = await fetch(process.env.SLACK_WEBHOOK_URL!, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
text: input.text,
blocks: input.blocksJson ? JSON.parse(input.blocksJson) : undefined,
}),
});
if (!res.ok) {
context.log.error(`Slack failed: ${res.status} ${await res.text()}`);
throw new Error(`Slack ${res.status}`);
}
}
);
Call it from a handler
The rindexer config…
chat:
slack:
- bot_token: ${SLACK_BOT_TOKEN}
channel: "#RethTransferEvents"
messages:
- event_name: Transfer
filter_expression: "value >= 10 && value <= 2000000000000000000"
template_inline: |
*New RETH Transfer Event*
from: {{from}}
to: {{to}}
amount: {{format_value(value, 18)}}
RETH contract: {{transaction_information.address}}
<https://etherscan.io/tx/{{transaction_information.transaction_hash}}|etherscan>
…becomes:
src/EventHandlers.ts
import { RocketPoolETH } from "generated";
import { sendSlack } from "./effects/slack";
import { formatUnits } from "./utils/format";
RocketPoolETH.Transfer.handler(async ({ event, context }) => {
const { from, to, value } = event.params;
if (value < 10n || value > 2_000_000_000_000_000_000n) return;
const text = [
`*New RETH Transfer Event*`,
`from: ${from}`,
`to: ${to}`,
`amount: ${formatUnits(value, 18)}`,
`RETH contract: ${event.srcAddress}`,
`<https://etherscan.io/tx/${event.transaction.hash}|etherscan>`,
].join("\n");
context.effect(sendSlack, { text });
});
For richer layouts (buttons, headers, dividers) build a Block Kit array and pass it as blocksJson: JSON.stringify(blocks).