Part 5 of 7 · Missed-call text-back series ~7 min read

How an unanswered call-back gets escalated

Most text-backs do their job: the caller replies and books. But some don’t — the message lands, nobody answers, and without a nudge that caller is exactly the one who quietly drifts away. This post is about the safety net: the scheduled sweep that notices a text-back has gone unanswered and puts the caller in front of a person to follow up.

Key takeaways

  • Some text-backs are never answered — and an unanswered text-back is a customer quietly slipping away, so the system watches for it.
  • An EventBridge Scheduler rule runs a sweep on a fixed cadence, looking for calls that were texted but have had no reply within a set window.
  • Each stale call is handed to a person to ring back, with the call time, the matched customer, and the text that went out attached.
  • The sweep escalates a call exactly once, respects quiet hours, and never sends the caller a second automated text.
  • It’s the difference between “we texted them” and “we got them back” — the net under the whole system.

The ones that go quiet

Most text-backs work: the caller reads it, taps the booking link or texts back, and Part 4 takes over. But some don’t. The text lands, the caller means to reply, and then the bus comes or the kettle boils and they forget. From the business’s side this looks identical to success — a text was sent — which is exactly why it’s dangerous. That caller had a need a few minutes ago and now they’re drifting, and nobody at the shop has any reason to notice. A system that only ever fires on incoming events would never see this, because the thing that needs acting on is an event that didn’t happen: a reply that never came.

Catching an absence needs something that runs on a clock rather than on a trigger. That’s the escalation sweep: a small scheduled job whose entire purpose is to find text-backs that have gone unanswered past a sensible window and put the caller in front of a person before they’re gone for good.

A job on a clock

The sweep is driven by EventBridge Scheduler — a managed cron that invokes a Lambda on a fixed cadence, with no always-on compute and effectively no cost. A sensible cadence is every 15 minutes during opening hours. Each run does the same simple thing: query the calls table for records that are texted but not replied, where the text-back went out longer ago than the no-reply window (say, 30 minutes) and which haven’t already been escalated. A short window catches people while their intent is still warm; making it configurable lets a business tune it — a restaurant taking bookings wants minutes, a tradesperson quoting jobs might be happy with a couple of hours.

For each call the sweep finds, it builds a handover and hands it to a person to ring back: the time of the missed call, the customer it was matched to (and their history, if any), the exact text-back that went out, and the fact that there’s been no reply. Then — and this is the important part — it marks the call escalated on the same record, so the next run 15 minutes later doesn’t flag the same call again. A call is escalated exactly once. The sweep raises a human, it does not send the caller a second automated text; the whole design rests on one text per missed call, and a chasing text would break that promise and read as nagging.

The no-reply sweep: a scheduled job finds texted-but-unanswered calls and escalates each once to a person On the left, a box “EventBridge Scheduler” labelled every 15 minutes during opening hours sends an arrow into a box “Sweep Lambda” inside a dotted AWS account container. The sweep Lambda queries a DynamoDB calls table for records in state texted-but-not-replied where the text-back is older than the no-reply window and not yet escalated. The matching records flow to a decision: for each stale call, an arrow goes to a box “Build handover” containing the call time, matched customer, the text-back sent, and no-reply. From there an arrow goes to a box “Notify a person to ring back” by SES email or push, and a second arrow writes back to the calls table marking the call escalated so it is never flagged twice. A small note beside the calls table reads quiet hours respected, escalate once. A bottom note reads: the sweep raises a human to follow up; it never sends the caller a second automated text. EventBridge every 15 min, opening hours AWS account Sweep Lambda find stale text-backs DynamoDB calls texted, no reply, past window query Build handover call time, matched customer, text sent, no reply each Notify a person ring back mark escalated The sweep raises a human to follow up — once per call — and never sends the caller a second automated text.
Fig 5. The no-reply sweep. EventBridge Scheduler runs the sweep on a fixed cadence; it queries for text-backs older than the no-reply window with no reply, builds a handover for each, notifies a person to ring back, and marks the call escalated so it’s only ever flagged once.

Why a sweep, and not a timer per call

You could imagine scheduling a one-off check for each individual text-back — set a 30-minute timer when the text goes out, fire it, see if there’s a reply. It works, but it means a scheduled entity per missed call, more moving parts to create and clean up, and a pile of near-simultaneous invocations on a busy morning. A single periodic sweep is simpler and cheaper: one rule, one function, one query that scales to whatever volume the day brings, and idempotent by design because the escalated flag means re-running it never double-notifies. At this scale the 15-minute granularity is plenty — the difference between a 30- and a 42-minute callback is nothing next to the difference between a callback and none.

The sweep also respects the same guardrails as everything else. It runs only during opening hours, so it doesn’t ping the owner’s phone overnight; a call missed at 11pm waits and is swept in the morning. It checks the opt-out list, so a number that texted STOP after the text-back is never escalated. And it touches only its own state — it reads calls and writes the escalated flag, nothing more — which keeps it safe to run unattended every quarter of an hour, forever.

Design rules that shaped escalation

  • Watch for the event that didn’t happen. A reply that never came is the signal; only a scheduled sweep can see an absence.
  • A clock, not a trigger. EventBridge Scheduler runs the sweep on a fixed cadence with no always-on compute.
  • Escalate once. The escalated flag on the call record makes the sweep idempotent — no call is ever flagged twice.
  • Raise a human, don’t chase the caller. The sweep notifies a person to ring back; it never sends a second automated text.
  • The same guardrails apply. Opening hours and the opt-out list are honoured by the sweep exactly as by the live path.
  • One sweep beats many timers. A single periodic query is simpler, cheaper, and idempotent than a scheduled entity per call.
All posts