

How to Broadcast Gmail Project Updates to Slack with Pipedream
Watches Gmail for labeled project-related emails and instantly forwards their sender, subject, and body snippet to the matching Slack channel.
Steps and UI details are based on platform versions at time of writing — check each platform for the latest interface.
Best for
Distributed teams that receive vendor emails or stakeholder feedback in Gmail and need the right Slack channel notified within seconds — without forwarding entire inboxes.
Not ideal for
Teams using Google Groups or shared inboxes where multiple accounts receive the same email; deduplication becomes complex and a dedicated email routing tool handles it better.
Sync type
real-timeUse case type
notificationReal-World Example
A 22-person product agency receives client feedback, vendor invoices, and contractor updates across three active projects — all landing in one project manager's Gmail. Before this workflow, the PM copy-pasted emails into Slack manually, often hours after receipt, and engineers missed blockers. Now, emails labeled 'Project-Alpha' trigger an instant post to #proj-alpha with the sender, subject line, and first 400 characters of the body — the team sees it in under 30 seconds.
What Will This Cost?
Drag the slider to your expected monthly volume.
Each platform counts differently — Zapier: 1 task per trigger. Make: 1 operation per module per record. n8n: 1 execution per run.





Prices shown for annual billing. Based on published pricing as of April 2026.
Estimated ROI
1000
min saved/mo
$583
labor value/mo
Free
no platform cost
Based on ~2 min manual effort per operation at $35/hr fully loaded labor cost.
Implementation
Import this workflow directly into Pipedream
Copy the pre-built Pipedream blueprint and paste it straight into Pipedream. All modules, filters, and field mappings are already configured — you just need to connect your accounts.
Before You Start
Make sure you have everything ready.
Field Mapping
Map these fields between your apps.
| Field | API Name | |
|---|---|---|
| Required | ||
| Email Subject | ||
| Sender Name and Email | ||
| Email Snippet / Body Preview | ||
| Email Timestamp | ||
| Gmail Label Name | ||
| Gmail Message ID | ||
| Target Slack Channel | ||
1 optional field▸ show
| Gmail Thread ID |
Step-by-Step Setup
pipedream.com > Workflows > New Workflow
Create a new Pipedream Workflow
Log into pipedream.com and click 'New Workflow' in the top-right corner. Give the workflow a clear name — 'Gmail → Slack Project Broadcaster' works well. You'll land on the workflow canvas with an empty trigger slot at the top. Pipedream workflows run top-to-bottom: trigger fires, then each step executes in order.
- 1Go to pipedream.com and sign in
- 2Click the blue 'New Workflow' button in the top-right
- 3Type 'Gmail → Slack Project Broadcaster' in the workflow name field
- 4Press Enter to confirm the name
Workflow Canvas > Add Trigger > Gmail > New Email
Add Gmail as the trigger source
Click the grey 'Add Trigger' block. Search for 'Gmail' in the app search bar and select it. Choose the 'New Email' trigger — this fires every time a new email arrives that matches your filter criteria. Pipedream uses Gmail's push notification API (not polling), so the trigger fires within 5–15 seconds of email delivery.
- 1Click the grey 'Add Trigger' block on the canvas
- 2Type 'Gmail' in the search bar
- 3Select 'Gmail' from the results
- 4Choose 'New Email' from the trigger list
Gmail Trigger > Connected Account > Connect Account
Connect your Gmail account
In the trigger configuration panel, click 'Connect Account' under the Connected Account field. A Google OAuth window will open — sign in with the Gmail account that receives project-related emails. Grant Pipedream the requested Gmail scopes. After connecting, the account email address appears in the dropdown and the field shows a green checkmark.
- 1Click 'Connect Account' in the Gmail trigger panel
- 2Select your Google account in the OAuth popup
- 3Click 'Allow' to grant Gmail read access
- 4Confirm the connected account appears in the dropdown
Gmail Trigger > Label > [your label name]
Filter emails by Gmail label
In the trigger's Label field, type the name of the Gmail label you use for project emails — for example, 'Project-Alpha'. If you manage multiple projects, you'll build separate workflows per label, or use a label prefix like 'Project-' and handle routing in a code step. Leave the Search Query field blank unless you need additional filtering (e.g., specific senders). Click 'Save and continue'.
- 1Click into the 'Label' field in the trigger config
- 2Type your exact Gmail label name (case-sensitive)
- 3Leave the Search Query field blank unless you need sender filtering
- 4Click 'Save and continue'
Gmail Trigger > Generate Test Event
Load a test email event
Click 'Generate Test Event' to pull a recent email from Gmail matching your label. Pipedream fetches the last matching message and displays its raw payload in the event inspector on the right side of the canvas. Expand the payload to confirm you can see fields like `subject`, `from`, `snippet`, `body`, and `labelIds`. You'll reference these field paths in later steps.
- 1Click 'Generate Test Event' in the trigger panel
- 2Wait 3–5 seconds for Pipedream to fetch from Gmail
- 3Click the event in the inspector panel to expand the payload
- 4Verify 'subject', 'from', and 'snippet' fields are visible
Workflow Canvas > + Add Step > Run Node.js code
Add a Node.js code step to build the Slack message
Click '+ Add Step' below the trigger, then select 'Run Node.js code'. This step extracts the relevant email fields and builds a formatted Slack Block Kit message. Using a code step here — rather than a pre-built action — lets you truncate the body snippet, strip HTML characters, and format the sender name cleanly. Paste the code from the Pro Tip section into the code editor.
- 1Click '+ Add Step' below the Gmail trigger block
- 2Click 'Run Node.js code' from the step type options
- 3Clear the default placeholder code in the editor
- 4Paste the Pro Tip code into the editor
Paste this into the Node.js code step (Step 6) — it extracts the Gmail event fields, strips HTML entities from the snippet, maps the Gmail label to the correct Slack channel, and returns a Block Kit payload ready to pass directly into the Slack 'Send Message' action. The `labelToChannelMap` object is where you add new projects — update it and redeploy without touching anything else.
JavaScript — Code Stepexport default defineComponent({▸ Show code
export default defineComponent({
async run({ steps, $ }) {
const email = steps.trigger.event;... expand to see full code
export default defineComponent({
async run({ steps, $ }) {
const email = steps.trigger.event;
// Map Gmail labels to Slack channel names
const labelToChannelMap = {
'Project-Alpha': '#proj-alpha',
'Project-Beta': '#proj-beta',
'Project-Gamma': '#proj-gamma',
};
// Find the matching project label from the email's label list
const projectLabel = email.labelIds?.find(label => labelToChannelMap[label]);
const channelName = projectLabel ? labelToChannelMap[projectLabel] : '#general-projects';
// Clean the snippet: strip HTML tags and decode common HTML entities
const rawSnippet = email.snippet || 'No preview available.';
const cleanSnippet = rawSnippet
.replace(/<[^>]+>/g, '')
.replace(/ /g, ' ')
.replace(/&/g, '&')
.replace(/</g, '<')
.replace(/>/g, '>')
.replace(/"/g, '"')
.trim()
.slice(0, 400);
// Format sender display name
const from = email.from || 'Unknown Sender';
const senderDisplay = from.replace(/<([^>]+)>/, '(<$1>)').trim();
// Format the received timestamp
const receivedDate = email.date
? new Date(email.date).toLocaleString('en-US', {
month: 'short', day: 'numeric', year: 'numeric',
hour: 'numeric', minute: '2-digit', timeZoneName: 'short'
})
: 'Unknown time';
// Build Slack Block Kit message
const slackBlocks = [
{
type: 'header',
text: { type: 'plain_text', text: '📧 New Project Email', emoji: true }
},
{
type: 'section',
fields: [
{ type: 'mrkdwn', text: `*From:*\n${senderDisplay}` },
{ type: 'mrkdwn', text: `*Channel:*\n${channelName}` }
]
},
{
type: 'section',
text: { type: 'mrkdwn', text: `*Subject:* ${email.subject || '(no subject)'}` }
},
{ type: 'divider' },
{
type: 'section',
text: {
type: 'mrkdwn',
text: `${cleanSnippet}${rawSnippet.length > 400 ? '…' : ''}`
}
},
{
type: 'context',
elements: [
{ type: 'mrkdwn', text: `Received: ${receivedDate} · Message ID: ${email.id}` }
]
}
];
return { channelName, slackBlocks, senderDisplay, receivedDate };
}
});channel: {{channel}}
ts: {{ts}}
Code Step > Test
Test the code step
Click 'Test' on the code step. Pipedream re-runs the step using the test event data loaded from Gmail in Step 5. The return value appears in the inspector panel on the right. Check that `slackBlocks`, `channelName`, and `senderDisplay` all have the expected values. If the snippet is showing HTML tags (e.g., ` `), the code step strips those — confirm the output looks clean.
- 1Click the 'Test' button inside the code step
- 2Wait 2–3 seconds for the step to execute
- 3Expand the 'Return Value' section in the right inspector
- 4Verify slackBlocks, channelName, and senderDisplay are populated correctly
Paste this into the Node.js code step (Step 6) — it extracts the Gmail event fields, strips HTML entities from the snippet, maps the Gmail label to the correct Slack channel, and returns a Block Kit payload ready to pass directly into the Slack 'Send Message' action. The `labelToChannelMap` object is where you add new projects — update it and redeploy without touching anything else.
JavaScript — Code Stepexport default defineComponent({▸ Show code
export default defineComponent({
async run({ steps, $ }) {
const email = steps.trigger.event;... expand to see full code
export default defineComponent({
async run({ steps, $ }) {
const email = steps.trigger.event;
// Map Gmail labels to Slack channel names
const labelToChannelMap = {
'Project-Alpha': '#proj-alpha',
'Project-Beta': '#proj-beta',
'Project-Gamma': '#proj-gamma',
};
// Find the matching project label from the email's label list
const projectLabel = email.labelIds?.find(label => labelToChannelMap[label]);
const channelName = projectLabel ? labelToChannelMap[projectLabel] : '#general-projects';
// Clean the snippet: strip HTML tags and decode common HTML entities
const rawSnippet = email.snippet || 'No preview available.';
const cleanSnippet = rawSnippet
.replace(/<[^>]+>/g, '')
.replace(/ /g, ' ')
.replace(/&/g, '&')
.replace(/</g, '<')
.replace(/>/g, '>')
.replace(/"/g, '"')
.trim()
.slice(0, 400);
// Format sender display name
const from = email.from || 'Unknown Sender';
const senderDisplay = from.replace(/<([^>]+)>/, '(<$1>)').trim();
// Format the received timestamp
const receivedDate = email.date
? new Date(email.date).toLocaleString('en-US', {
month: 'short', day: 'numeric', year: 'numeric',
hour: 'numeric', minute: '2-digit', timeZoneName: 'short'
})
: 'Unknown time';
// Build Slack Block Kit message
const slackBlocks = [
{
type: 'header',
text: { type: 'plain_text', text: '📧 New Project Email', emoji: true }
},
{
type: 'section',
fields: [
{ type: 'mrkdwn', text: `*From:*\n${senderDisplay}` },
{ type: 'mrkdwn', text: `*Channel:*\n${channelName}` }
]
},
{
type: 'section',
text: { type: 'mrkdwn', text: `*Subject:* ${email.subject || '(no subject)'}` }
},
{ type: 'divider' },
{
type: 'section',
text: {
type: 'mrkdwn',
text: `${cleanSnippet}${rawSnippet.length > 400 ? '…' : ''}`
}
},
{
type: 'context',
elements: [
{ type: 'mrkdwn', text: `Received: ${receivedDate} · Message ID: ${email.id}` }
]
}
];
return { channelName, slackBlocks, senderDisplay, receivedDate };
}
});Workflow Canvas > + Add Step > Slack > Send Message
Add the Slack 'Send Message' action
Click '+ Add Step' below the code step and search for 'Slack'. Select the 'Send Message' action. Connect your Slack workspace via the Connected Account dropdown — this opens a Slack OAuth screen where you authorize Pipedream to post messages. In the Channel field, reference the output from your code step: click the '{}' icon and select `steps.build_slack_message.$return_value.channelName`. In the Blocks field, select `steps.build_slack_message.$return_value.slackBlocks`.
- 1Click '+ Add Step' below the code step
- 2Search for 'Slack' and select it
- 3Choose 'Send Message' from the action list
- 4Click 'Connect Account' and authorize your Slack workspace
- 5Set Channel to `steps.build_slack_message.$return_value.channelName`
- 6Set Blocks to `steps.build_slack_message.$return_value.slackBlocks`
Slack Action > Test
Test the Slack action
Click 'Test' on the Slack action step. Pipedream sends the formatted Block Kit message to your Slack channel using the test event data. Switch to Slack and look for the message in the target channel — it should appear within 5 seconds. Verify the sender name, subject, timestamp, and body snippet all display correctly. If the message posts but Block Kit formatting looks broken, check the slackBlocks JSON structure in the inspector.
- 1Click 'Test' inside the Slack action step
- 2Open Slack and navigate to your target project channel
- 3Confirm the message appears with correct formatting
- 4Check the inspector for any error responses from the Slack API
Workflow Canvas > Deploy
Deploy the workflow
Click the grey 'Deploy' button in the top-right of the workflow canvas. Pipedream registers the Gmail push notification subscription and activates the workflow. The status indicator in the top bar changes from 'Inactive' to 'Active' with a green dot. From this point, every new email with your label triggers the workflow and posts to Slack automatically — no manual intervention needed.
- 1Click the grey 'Deploy' button in the top-right corner
- 2Confirm the status indicator turns green and shows 'Active'
- 3Send a test email to your Gmail with the project label applied
- 4Verify the Slack message appears within 30 seconds
Workflow > Runs Tab > Settings > Notifications
Monitor runs in the Pipedream inspector
Navigate to your workflow and click the 'Runs' tab to see every execution. Each run shows the Gmail payload that triggered it, the output of your code step, and the Slack API response. If a run fails, the failing step is highlighted in red with the error message. Set up error notifications under Settings > Notifications to get an email when the workflow errors — critical for catching Gmail subscription lapses or Slack token expiry.
- 1Click the 'Runs' tab at the top of your workflow
- 2Click any run to expand its step-by-step execution details
- 3Navigate to Settings > Notifications
- 4Enable email alerts for workflow errors
Going live
Production Checklist
Before you turn this on for real, confirm each item.
Troubleshooting
Common errors and how to fix them.
Frequently Asked Questions
Common questions about this workflow.
Analysis
Use Pipedream for this if your team has even one engineer who can read JavaScript. The Node.js code step is the entire reason to pick Pipedream here — you get HTML stripping, label-to-channel routing, and Block Kit formatting in a single step that takes 20 minutes to write and runs in under 200ms. The Gmail push notification integration fires in under 15 seconds from email delivery. The one scenario where you'd pick something else: if your team is entirely non-technical and needs someone to maintain this long-term, Zapier's no-code Gmail trigger and Slack action get you 80% of the way there with zero code — you just lose the formatting control and routing logic.
Pipedream's pricing for this workflow is straightforward. Each run consumes roughly 2–3 credits (one for the trigger, one for the code step, one for the Slack action). At 200 project emails per month — a busy agency with 5 active projects — that's 400–600 credits/month. Pipedream's free tier includes 10,000 credits/month. You'd need to receive roughly 3,300 project emails per month before hitting the free limit. The paid Basic plan at $19/month gives you 100,000 credits. Zapier's equivalent — Gmail trigger + Slack action — costs one task per run, and at 200 emails/month you'd burn through the free tier's 100-task limit in a day. Zapier's Starter plan at $29.99/month gives you 750 tasks. Pipedream is cheaper at any meaningful volume.
Zapier's Gmail trigger is slightly easier to configure for non-coders — the label filter UI is more forgiving and doesn't require exact case matching. Make's scenario builder lets you visually route emails to different Slack channels using a Router module, which is more intuitive than a JavaScript object map if you have many projects. n8n's Gmail node gives you full access to the raw MIME payload, which is better if you need to process attachments or parse structured email bodies. Power Automate has a native Gmail connector but it's slower — polling every 1–5 minutes instead of push — and the Slack connector is limited in scope. Pipedream wins here because the code step collapses what would be 3–4 Make modules or a complex n8n Function node into clean, readable JavaScript that's easy to hand off to another engineer.
Three things you'll hit after this is running in production. First, Gmail occasionally fires duplicate push events for the same email — specifically when a filter applies a label and then another rule modifies it within the same second. Without the Message ID deduplication check in the code step, you'll see two identical Slack messages. Add it before you go live. Second, the Gmail push notification subscription silently expires if your Pipedream workflow errors continuously for more than 24 hours — the subscription renewal fails and you stop getting events with no obvious error in the UI. Set up error notifications and check the Runs tab weekly. Third, Slack's Block Kit `section` fields have a 2,000-character limit per text element — if you ever extend the snippet beyond 400 characters without a truncation check, the Slack API returns a `invalid_blocks` error that isn't immediately obvious from the error message alone.
Ideas for what to build next
- →Add an email reply link to the Slack message — Include a 'Reply in Gmail' button in the Block Kit message using the email's message ID to build a deep link (`https://mail.google.com/mail/u/0/#inbox/{messageId}`). This lets team members respond directly from the Slack notification without searching their inbox.
- →Route to multiple channels based on sender domain — Extend the code step to check the sender's email domain in addition to the label — so emails from `@vendorA.com` always go to #vendor-a even if mislabeled. Add a secondary routing map keyed by domain and merge the two routing signals with a fallback.
- →Build a daily digest instead of instant notifications — Replace the Gmail push trigger with a Pipedream scheduled trigger that runs at 8 AM. Use the Gmail search action to pull all project-labeled emails from the last 24 hours, batch them by project label, and post a single digest message per channel — reducing Slack noise for lower-urgency projects.
Related guides
How to Share Notion Meeting Notes to Slack with Pipedream
~15 min setup
How to Share Notion Meeting Notes to Slack with Power Automate
~15 min setup
How to Share Notion Meeting Notes to Slack with n8n
~20 min setup
How to Send Notion Meeting Notes to Slack with Zapier
~8 min setup
How to Share Notion Meeting Notes to Slack with Make
~12 min setup
How to Create Notion Tasks from Slack with Pipedream
~15 min setup