Deliverability triage board for your Customer.io sending
See which email providers and campaigns are hurting your sending reputation each morning, then suppress bad addresses and log the cleanup.
Build me a deliverability triage board for our Customer.io workspace that our lifecycle marketer opens every morning. It is one app with a date window picker at the top, a rollup area that summarizes failures two different ways, and a detail list of the individual bad deliveries underneath. The job of the board is to answer one question fast: which receiving email provider or which campaign is dragging our sending reputation down right now, and what do I do about it.
Data comes from Customer.io List Messages, which returns delivery records and their metrics. When the board loads, page through the messages in the selected date window and keep two sets of numbers. First, the failures: records whose metric is bounced, spammed (that is the spam complaint metric), dropped, failed or undeliverable. Second, the total volume actually sent or delivered in the same window, because that is the denominator for every rate on the board. Do not compute a bounce rate against failures alone. If the volume numbers cannot be loaded for some slice, show the raw counts and mark the rate as unavailable rather than showing a made up percentage.
Respect the API limits when loading. The messages endpoint is cursor paginated: the response carries a next token that has to be passed back as the start query parameter on the following call, and you iterate until next comes back empty. Page size defaults to 50 and can go up to 1000, so use a large page size to cut the number of round trips. The App API is rate limited to 10 requests per second per workspace, so pace the paging, back off and honor Retry-After if a 429 comes back, and show a progress indicator while a wide date window is loading instead of freezing the screen. Page rather than trying to pull the entire history at once.
The first rollup is by receiving email provider. Derive the provider from the domain part of each recipient address, so gmail.com, outlook.com, yahoo.com, hotmail.com, icloud.com and any other high volume domain each get their own row, and group the long tail into an other row that can be expanded. Each row shows total volume sent to that provider in the window, the count of each failure type, the bounce rate and the complaint rate. Sort so the worst offenders sit at the top by default.
The second rollup is by the campaign or newsletter that sent the message. Group the same delivery records by whatever campaign, newsletter or broadcast identifier the records carry, and label each row with the campaign or newsletter name when the record has one, falling back to the identifier and the subject line when it does not. Same columns as the provider table: volume, failure counts by type, bounce rate, complaint rate. A marketer should be able to glance between the two tables and tell the difference between a provider wide problem and one bad campaign.
Bake in a red flag rule. Any row where the bounce rate crosses 2 percent or the complaint rate crosses 0.1 percent gets visibly flagged, in both the provider table and the campaign table. Make both thresholds editable in settings and store the values, but ship with 2 percent and 0.1 percent as the defaults. Suppress the flag on rows with a tiny sample size where a single bounce would blow past the threshold, and show the volume so the user can judge for themselves.
Clicking any provider row or campaign row filters the detail list underneath to just that slice. The detail list shows one line per failed delivery: recipient email address, provider, campaign or newsletter, failure type, subject and the timestamp. It supports multi select with checkboxes and a select all for the current filter.
From any address in the detail list I can permanently suppress that person using Customer.io Suppress Person. This action is destructive and needs to be treated that way. Suppression permanently deletes the person and blocks that identifier from ever being recreated, and there is no undo. So the confirmation dialog must state that plainly and require me to type the full email address exactly before the confirm button becomes active. After a successful suppression, mark that address as suppressed in the board so it is obvious it has already been handled, and keep a record of who suppressed it and when.
With a batch of failures selected, an action appends them to our remediation log using Google Sheets Append Values. One row per failure, with the date, recipient email, provider, campaign or newsletter, failure type, subject and whether we suppressed the person. The spreadsheet and tab are configured once in settings and reused, and each append adds to the bottom of the existing log rather than overwriting it.
A post summary action sends the day's rollup to our marketing ops channel with Slack Bot Send a Message. The message covers the date window, total sends, overall bounce and complaint rate, the flagged providers and flagged campaigns with their rates, and how many addresses were suppressed and logged in this session. Keep it short enough to read in the channel without opening anything.
Remember each user's last used date window and their threshold settings so the board opens the same way tomorrow morning, and keep the suppression and log history so the team can see what was already actioned on previous days.
What does this prompt do?
- Pulls your recent Customer.io delivery failures, including bounces, spam complaints, drops and send failures, for any date window you pick
- Rolls them up two ways, by receiving email provider like Gmail, Outlook and Yahoo, and by the campaign or newsletter that sent them, with volume plus bounce and complaint rate on every row
- Raises a red flag on any provider or campaign above 2 percent bounces or 0.1 percent spam complaints, so you can see what is dragging your reputation down
- Lets you permanently suppress a bad address, add a batch of failures to a Google Sheets cleanup log, and post the morning summary to your marketing ops Slack channel
What do I need to use this?
- A Customer.io workspace you send email from, plus its API credentials
- A Google Sheets spreadsheet to act as your remediation log
- A Slack workspace and a channel for marketing ops updates
- A few weeks of sending history in Customer.io so the rates mean something
How can I customize it?
- Change the red flag thresholds from 2 percent bounces and 0.1 percent complaints to whatever standard your team holds itself to
- Set the date window the board opens on, such as yesterday only or a rolling seven days
- Choose which failure types count as a problem, and which providers get their own row instead of falling into the grouped long tail
- Point the cleanup log at a different spreadsheet tab, or the daily summary at a different Slack channel
FAQs
Can I undo a suppression?
Where do the provider groups come from?
What counts as a bad bounce rate?
Does the board change anything in Customer.io by itself?
Will it handle a big sending volume?
Who is this for?
Related templates
Stop buying stale lists. Reps run a saved search, work the results like an inbox, and only the accounts they approve ever reach your CRM.
See how your brand's news coverage and sentiment stack up against four competitors, then let an assistant write the weekly report for you.
One screen showing every social post waiting on approval, sorted by deadline, so reviewers can approve or reject without leaving the page.
Every Monday, find the past champions and closed-won contacts who changed jobs, update Attio, and get the moves worth chasing in Slack.
Staff submit what happened, your social manager edits the copy, picks the accounts and puts it on the calendar without a single spreadsheet.
Drag creators through Sourced to Wrapped on a board grouped by campaign, with audience stats on every card and a one-click brief for each creator.
Stop guessing which campaign is burning your sending reputation.
Open one board each morning, see the providers and campaigns dragging you down, and clean up the bad addresses in a few clicks.