Never Miss a Stripe Payment Again — Real-Time Alerts on Slack, Discord and Telegram with n8n
Stripe processes the payment. You find out 3 hours later when you check your dashboard.
For solo founders and small teams, missing real-time payment events isn't just inconvenient — it means slower fulfillment, delayed onboarding, and missed opportunities to catch failed payments before customers churn.
This tutorial shows how to build a Stripe → multi-channel alert system with n8n that notifies your whole team instantly, in whichever app you actually use.
What Gets Alerted
The workflow listens to five Stripe webhook events:
| Event | What it means | Who cares |
|---|---|---|
payment_intent.succeeded |
Customer paid | Everyone 🎉 |
payment_intent.payment_failed |
Card declined | Support team |
charge.refunded |
Refund issued | Finance |
customer.subscription.deleted |
Subscription cancelled | Sales/CS |
invoice.payment_failed |
Recurring payment failed | Finance |
Each event generates a formatted message delivered simultaneously to Slack, Discord, Telegram, and/or email — your choice.
The Slack Message Format
Instead of raw JSON, the alerts are formatted for humans:
💰 New Payment
Amount: €149.00
Customer: Acme Corp (billing@acme.com)
Product: Professional Plan
Payment ID: pi_3abc...
Time: 26 Jul 2026, 14:32
For failed payments:
⚠️ Payment Failed
Amount: €149.00
Customer: john@example.com
Reason: insufficient_funds
Retry: Stripe will retry in 3 days
Payment ID: pi_3xyz...
n8n Setup
1. Stripe Webhook
In your Stripe Dashboard → Developers → Webhooks → Add endpoint:
Endpoint URL: https://your-n8n.com/webhook/stripe-alerts
Events to send: Select the 5 events listed above
Copy the Signing Secret — you'll need it to verify webhook authenticity.
2. Webhook Verification (Security)
Always verify Stripe webhooks. n8n's built-in Stripe Trigger node handles this automatically. If you're using a plain Webhook node, add this verification in a Code node:
const stripe = require('stripe'); // not available in n8n — use the Stripe Trigger node instead
Use the Stripe Trigger node — it handles signature verification out of the box. Don't use a plain Webhook node for Stripe.
3. The Event Router
After the Stripe Trigger, add a Switch node that routes on {{$json.type}}:
-
payment_intent.succeeded→ Branch 1 -
payment_intent.payment_failed→ Branch 2 -
charge.refunded→ Branch 3 -
customer.subscription.deleted→ Branch 4 -
invoice.payment_failed→ Branch 5
Each branch formats the message and sends to your channels.
4. Message Formatting (Code Node)
const event = $input.first().json;
const type = event.type;
const obj = event.data.object;
let emoji, title, details;
if (type === 'payment_intent.succeeded') {
emoji = '💰';
title = 'New Payment';
const amount = (obj.amount / 100).toFixed(2);
const currency = obj.currency.toUpperCase();
details = `Amount: ${currency} ${amount}\nCustomer: ${obj.customer || 'Guest'}\nID: ${obj.id}`;
} else if (type === 'payment_intent.payment_failed') {
emoji = '⚠️';
title = 'Payment Failed';
const amount = (obj.amount / 100).toFixed(2);
const reason = obj.last_payment_error?.message || 'Unknown reason';
details = `Amount: ${obj.currency.toUpperCase()} ${amount}\nReason: ${reason}\nID: ${obj.id}`;
} else if (type === 'charge.refunded') {
emoji = '↩️';
title = 'Refund Issued';
const amount = (obj.amount_refunded / 100).toFixed(2);
details = `Amount refunded: ${obj.currency.toUpperCase()} ${amount}\nCustomer: ${obj.customer || 'Guest'}`;
}
const message = `${emoji} *${title}*\n${details}\n_${new Date().toLocaleString('en-GB')}_`;
return [{ json: { message, type, raw: obj } }];
5. Multi-Channel Delivery
Connect the formatted message to all your channels in parallel (use Merge node if you want a single execution path):
Slack — HTTP Request:
POST https://hooks.slack.com/services/YOUR/WEBHOOK/URL
Body: { "text": "{{$json.message}}" }
Discord — HTTP Request:
POST https://discord.com/api/webhooks/YOUR_WEBHOOK_URL
Body: { "content": "{{$json.message}}" }
Telegram — HTTP Request:
POST https://api.telegram.org/botYOUR_TOKEN/sendMessage
Body: { "chat_id": "YOUR_CHAT_ID", "text": "{{$json.message}}", "parse_mode": "Markdown" }
6. Google Sheets Logging
Every event also appends a row to your Sheets log:
Timestamp | Event Type | Amount | Currency | Customer Email | Payment ID | Status
This gives you a complete audit trail outside Stripe — useful for reconciliation, and for team members who don't have Stripe access.
Filtering by Amount (Optional)
Don't want a Slack notification for every $1 microtransaction? Add an IF node before the Slack branch:
// Only alert Slack for payments over €50
return $json.raw.amount > 5000; // Stripe amounts in cents
Discord can still log everything, Slack only gets the significant ones.
Estimated Setup Time
- Stripe webhook: 5 minutes
- n8n workflow import and configure: 10 minutes
- Slack/Discord/Telegram webhook URLs: 5 minutes each
- Test with Stripe's webhook simulator: 5 minutes
Total: ~30 minutes to first real-time alert.
Get the Pre-Built Workflow
The complete workflow with all 5 event types, formatting logic, and multi-channel delivery configured is available at n8nmarkets.com. Search "Stripe Payment Alerts Slack Discord SMS Email Sheets".
Includes the workflow JSON ready to import, plus setup guide for each notification channel.
Which Stripe events do you find most useful to monitor in real-time? For most SaaS teams it's failed payments — catching those within minutes instead of hours dramatically improves recovery rates.
Top comments (0)