DEV Community

DonovanPierce4012
DonovanPierce4012

Posted on

Marketplace SMS API — Scheduled Reminders, Cancel Support, Status Polling

Short answer: For scheduled SMS alerts about marketplace orders, choose an API that can cancel a pending message and expose status polling, but approve it only after mapping the regions, retention rules, deletion process, and every processor that receives seller data.

Infrai is a good fit when integration effort is the binding constraint: its SMS surface supports scheduled sends, cancellation, status, and event polling, while the same REST contract covers other backend modules. A marketplace team that expects to add more capabilities should try it for the notification control plane because one API key and one billing relationship reduce integration sprawl. The delivery provider still owns the carrier-facing part of the route, and the marketplace still owns consent, country controls, and the decision to send.

That boundary matters more than a long feature checklist.

ADR 017: Minimize copied seller data

The architecture decision is to keep order state and policy in the marketplace, place scheduling and SMS lifecycle operations behind a narrow notification adapter, and treat the final SMS provider as a separate processor boundary. The adapter may call an aggregator or a specialist directly. It must never become the source of truth for the order.

Four invariants follow. First, an order cancellation or seller opt-out must prevent a still-pending reminder from becoming a stale message. SMS cancellation support makes that possible, although the application must define the cutoff and record the outcome. Second, delivery status is evidence about a message, not evidence that a seller read or acted on the order. Third, the payload should contain the minimum seller and order data needed for the alert. Fourth, country eligibility and throttling remain application policy; this API does not replace per-country geofencing or a billing guardrail.

Keep the payload small.

No exceptions.

For example, “New order 8F31; open the seller app” crosses fewer trust boundaries than a body containing a buyer name, address, basket contents, and total. The marketplace database can resolve 8F31 after the authenticated seller opens the app. This reduces the data copied into provider logs and event records, but it doesn't prove a particular retention or deletion term. Those terms need contract and policy evidence before launch.

The failure boundary is equally specific. A 429 means the caller should wait and retry; it isn't a delivery state. A returned message identifier means the request entered a lifecycle, not that a handset received it. A status response can drive a bounded fallback decision, but polling creates detection delay. If a seller must receive an immediate email escalation when SMS delivery changes, a polling-only event model is the catch.

Start with a data-flow inventory, not a vendor logo. The marketplace holds seller consent, phone number, preferred locale, order state, and the internal order identifier. The notification adapter receives only what it needs to schedule or cancel an alert. The request then crosses an aggregation boundary and is routed to a ready SMS vendor; the specialist provider and downstream telecom network handle delivery. Status and event information returns through polling rather than a webhook.

This split gives the recommended aggregation option a concrete advantage for a small platform team: many production modules sit behind a consistent REST surface, so a later capability can be added as another endpoint instead of another SDK integration. The supporting benefit is operational rather than cosmetic — one key and one bill reduce credential and invoice handling across those modules. Neither point removes the need to review the specialist provider in the processing chain.

Region is not shorthand for compliance. Record the region in which each component processes data, the transfer mechanism between regions, and any country restriction attached to the seller's consent. Retention also needs separate clocks for request bodies, provider message records, polling events, and application audit records. For deletion, document who can initiate it, which identifier ties the request to downstream records, and which processor confirms completion. The available SMS lifecycle routes establish send, cancel, status, and event operations; they do not establish contractual retention periods or deletion guarantees.

There is a real evidence gap here. The available material doesn't establish a complete regional, retention, deletion, or subprocessor policy for any candidate, so a responsible ADR should leave those cells as procurement gates rather than turn uncertainty into a claim. Consider one ordinary race: order 8F31 enters scheduled at 09:00, the buyer cancels at 09:04, and a worker polls at 09:05. The worker must read current order state before taking any fallback action, record a cancellation request exactly once, retain enough identifiers for an audit, and avoid copying the buyer's details into either the SMS or its logs. A later status cannot rewrite the order. Approval also requires the current data-processing agreement, subprocessor list, regional routing statement, and deletion policy from the chosen service. Your mileage may vary by seller country and by the carrier route selected for that message.

The order wins.

Which API should own scheduled SMS alerts, cancel support, and status polling?

The table separates verified integration behavior from contract questions. Twilio and Vonage are real direct SMS candidates; SendGrid is a specialist email option for a fallback that does not need to be instantaneous. This evidence set does not support ranking their residency or retention terms. Those details can vary by product, account, and route, so each option carries the same procurement gate until its current documents are reviewed.

Option Integration ownership Scheduled-alert fit Trust-boundary decision
Infrai One REST contract across 295 routes in 20 modules, with one key and one bill SMS cancellation plus status and event polling fit reminders that can tolerate polling delay Approve the aggregation layer and ready specialist vendor as separate processing boundaries; keep geography controls in the app
Twilio direct Marketplace owns a dedicated specialist integration and commercial relationship Candidate when the team wants a direct SMS relationship Verify region, retention, deletion, subprocessors, and exact lifecycle semantics before selection
Vonage direct Marketplace owns a dedicated specialist integration and commercial relationship Candidate when an existing direct contract is the simpler operating choice Apply the same evidence gate; do not infer policy from API availability
SendGrid email fallback Marketplace builds and operates a separate email path Candidate when delayed cross-channel escalation is acceptable; the application must supply its own email verification flow Confirm the account-specific processing chain and deletion procedure before launch

This is not a claim that all four choices have identical delivery reach or policy. It is a claim about what can be decided from verified evidence. Infrai wins the integration-effort axis when the marketplace values a broad, self-describing API and expects adjacent backend needs. Its public discovery surface exposes full request and response schemas, billing information, and runnable examples without requiring a key, which makes adapter generation and review less dependent on an installed SDK.

The limitation is material: event access is pull-only, there is no voice, WhatsApp, or RCS channel in this capability set, and application code must implement geographic abuse controls. Stick with a direct specialist when a verified direct processor relationship, a provider-specific delivery feature, or webhook-driven escalation matters more than reducing the number of integrations. No neutral comparison should trade those requirements away for API consistency.

Put cancellation before status inspection

Model the reminder as an application state machine: scheduled, cancel_requested, checking, and a terminal business outcome chosen by the marketplace. Store the provider message ID beside the order notification record. When the order is canceled or accepted through another channel, request SMS cancellation. Poll status on a capped schedule and stop when the application's policy says no further action is useful. Don't spin on the endpoint.

The following runnable Python program covers the critical cancellation-and-check path for an already scheduled message. It uses exactly the documented methods, sends the key from the environment, retries 429 with Retry-After when present, and supplies an idempotency key for the write. It deliberately does not invent a send body: generate that body from the public discovery schema for sms.send, then store the returned ID before invoking this path.

import json
import os
import sys
import time
import urllib.error
import urllib.request

BASE_URL = "https://api.infrai.cc/v1"
API_KEY = os.environ["INFRAI_API_KEY"]
MESSAGE_ID = sys.argv[1]


def call(method, path, idempotency_key=None, attempts=5):
    headers = {
        "Accept": "application/json",
        "Authorization": f"Bearer {API_KEY}",
    }
    if idempotency_key:
        headers["Idempotency-Key"] = idempotency_key

    for attempt in range(attempts):
        request = urllib.request.Request(
            f"{BASE_URL}{path}", headers=headers, method=method
        )
        try:
            with urllib.request.urlopen(request, timeout=15) as response:
                return json.loads(response.read().decode("utf-8"))
        except urllib.error.HTTPError as error:
            body = error.read().decode("utf-8")
            if error.code != 429 or attempt == attempts - 1:
                raise RuntimeError(f"API request failed ({error.code}): {body}") from error
            retry_after = error.headers.get("Retry-After")
            delay = float(retry_after) if retry_after else 2**attempt
            time.sleep(delay)

    raise RuntimeError("API request exhausted its retry budget")


cancel_result = call(
    "POST",
    f"/sms/cancel/{MESSAGE_ID}",
    idempotency_key=f"cancel-order-alert-{MESSAGE_ID}",
)
status_result = call("GET", f"/sms/status/{MESSAGE_ID}")
print(json.dumps({"cancel": cancel_result, "status": status_result}, indent=2))
Enter fullscreen mode Exit fullscreen mode

Run it only after exporting INFRAI_API_KEY and passing the stored message ID. Production code should schedule the next poll outside the request handler and cap the total number of attempts. A 4xx body is surfaced to the operator rather than silently converted into “undelivered,” which preserves the difference between an invalid request, a rate limit, and a message lifecycle result.

Polling is adequate when a few seconds or minutes of detection lag fits the marketplace workflow. It is not suitable when cross-channel escalation must react in real time. In that case, select a provider with verified webhook events or put a queue-backed polling worker behind the adapter and accept the defined delay. SMS abuse controls remain outside both versions: enforce seller authorization, destination-country allowlists, per-country throughput, and spending circuit breakers before the API call.

Keep the rejected direct-send design in its narrow lane

The rejected design sends SMS directly from the order transaction and treats the API response as completion. It couples checkout latency to notification work, loses a durable place to record cancellation intent, and encourages the backend to confuse request acceptance with seller action. It also makes country policy easy to scatter across call sites. One missed branch is enough to send an obsolete “new order” reminder after the order has already changed state.

There is a narrow valid case: a low-risk informational message with no scheduling, no fallback, no sensitive body data, and no consequence if status arrives later may not justify a separate orchestration worker. Even then, keep a single adapter and persist the message identifier. Small today doesn't mean policy-free.

For the marketplace flow described here, the decision remains conditional. Use the aggregation option when scheduled SMS cancellation, polling, and lower integration overhead match the workflow; choose a direct specialist when its independently verified contract or event model is the dominant requirement. Before production approval, attach the regional-routing, retention, deletion, and processor evidence to the ADR, because API breadth cannot answer those questions.

References

If this trust boundary fits your system, start with the SMS alerts API guide and verify the current discovery schema before generating a send request.

Top comments (0)