Daily weather bulletins for six regions: a month of TTS, MAI vs Sume

Six regional bulletins of 260 characters, every day for 30 days: 46,800 characters, $0.70 on MAI Flash, $1.03 on MAI-Voice-2.1, $2.22 on Sume TTS.

5 min readSume
All posts

Six regional weather bulletins of 260 characters each, every day for 30 days, come to 46,800 characters and cost $0.70 on MAI-Voice-2.1-Flash, $1.03 on MAI-Voice-2.1 and $2.22 on Sume TTS 1.0. At list rates that is 46,800 characters: $1.03 on MAI-Voice-2.1 ($22 per 1M characters), $0.702 on MAI-Voice-2.1-Flash ($15 per 1M), and $2.22 on Sume TTS 1.0 ($47.50 per 1M, or $0.0475 per 1,000 characters).

The inputs are assumptions for this scenario: six regions, 260 characters per bulletin, one job per bulletin, 30 days. Microsoft's prices are from its announcement page and Sume's from the API reference and pricing page, all read 2026-10-05. The totals are rate times characters, before any per-job rounding.

What the bill looks like

The one-run column is one day of six bulletins (1,560 characters), so the monthly total is thirty of those days.

Cost of 1,560 characters, and of 46,800 characters over 30 days, at list rates (read 2026-10-05)
ModelRate per 1M charactersOne runTotal over 30 days
MAI-Voice-2.1$22.00$0.034$1.03
MAI-Voice-2.1-Flash$15.00$0.023$0.702
Sume TTS 1.0$47.50$0.074$2.22

A scheduled batch is a jobs problem, not a latency problem

A bulletin that is generated at 6 a.m. and published at 7 a.m. does not need a first-audio time measured in milliseconds. It needs six jobs that finish reliably and can be found again if a step fails. Microsoft's model page quotes about 45 ms for Flash and about 550 ms for MAI-Voice-2.1, which matter for live agents; Sume TTS 1.0 is an asynchronous job with status and result URLs.

  • Use a stable Idempotency-Key per region and date such as weather-2026-10-05-north, so a retried cron run returns the original job instead of billing twice.
  • Poll status_url, stop when terminal is true, and read the result only when sume_status is completed.
  • Each bulletin is far below the 20,000-character request limit, so there is nothing to split.
  • Set language explicitly when a region reads in a language other than English; omitted, it defaults to English.

Run it on Sume

This loops over the regional texts and uses the date in each idempotency key. A second run of the same morning job reuses the jobs it already created.

import os, time, requests

API = "https://api.sume.com"
H = {"Authorization": f"Bearer {os.environ['SUME_API_KEY']}"}

def speak(text, key, **extra):
    body = {"transcript": text, "language": "en", **extra}
    body.setdefault("avatar_handle", os.environ.get("SUME_AVATAR_HANDLE", ""))
    r = requests.post(f"{API}/v1/tts-1.0/generate", timeout=60,
                      headers={**H, "Idempotency-Key": key}, json=body)
    r.raise_for_status()
    job = r.json()["data"]
    while True:
        s = requests.get(job["status_url"], headers=H, timeout=30).json()["data"]
        if s["terminal"]:
            break
        time.sleep(s["next_poll_after_seconds"] or 2)
    if s["sume_status"] != "completed":
        raise RuntimeError(s["sume_status"])
    res = requests.get(job["result_url"], headers=H, timeout=30).json()["data"]["result"]
    return res

bulletins = {"north": "Cloudy with light rain, high of 14.", "south": "Sunny spells, high of 19."}
for region, text in bulletins.items():
    res = speak(text, f"weather-2026-10-05-{region}")
    print(region, res["artifacts"][0]["url"])

When MAI is the better pick

If the bulletins are read live into a phone line or a smart speaker, Microsoft's Flash positioning for latency-sensitive use is the right fit and Sume's job model is not. For a published audio file, the price gap here is about $1.52 a month between Flash and Sume, and the question is whether one API for voice, captions and video is worth that.

Sources

Related posts

More in Pricing

All Pricing posts

Written by Sume