Turn every WordPress post into a narrated audio version

By General Input

A studio your content team opens after publishing to clean up the script, pick a voice, and ship a listenable version of every post.

Integrations

  • Deepgram
  • WordPress
  • Cloudinary

Type

App

Categories

  • Marketing
  • Operations

Build me an audio version studio that my content team opens whenever we publish, so every blog post gets a listenable version without anyone touching recording gear. The people using this are writers and editors, not developers, so the app should read like a production tool: a queue of work, a script to clean up, a voice to pick, and an approve button that ships it.

The home screen is the queue. Pull posts from WordPress with List Posts, filtered by status and date range, defaulting to published posts from the last 90 days. Each row shows the title, publish date, approximate word count, and a badge marking whether narration has already shipped for that post. Give it three tabs: Needs audio (published posts with no approved take, oldest first so the backlog actually gets worked through), All posts, and Shipped. Add a title search box. The badge and the Needs audio tab are driven by the app's own records rather than anything stored in WordPress, matched on the WordPress post ID.

Opening a post loads its full body with Retrieve a Post and drops it into an editable script pane, with the original post rendered read-only beside it for reference. On first open, auto-clean the text: strip HTML tags and shortcodes, remove image captions and figure text, drop navigational furniture like Read more links, and collapse leftover whitespace. From there the team edits by hand, which is the part that matters most: trimming the intro, respelling names and product terms so they are pronounced correctly, and expanding abbreviations that would otherwise be read out letter by letter. Every save creates a new script version with a timestamp and the person who saved it, so nothing is lost and you can always see what shipped.

Split the script into sections, either on headings or on a manual split marker the editor can insert. Each section shows its own character count and can be narrated on its own, so fixing one paragraph does not mean re-narrating a 2,000 word post while you are still iterating.

Above the Generate button, show a voice picker listing the Deepgram Aura voices with a short descriptor for each, the live character count for the whole script and for the selected section, and an estimated cost for the generation. Work the estimate out as characters multiplied by a per-million-character rate stored in app settings, so an admin can keep it accurate as pricing changes, and always show it before the team spends anything.

Generate sends the edited script, or a single section, to Deepgram Text to Speech. Keep every generation as a take and never overwrite one. A take records the voice and model used, the script version it came from, the character count, the estimated cost, who requested it, when, and the x-request-id from the response for support tickets. Render the takes as a list with inline audio players so the team can play two voices back to back and pick one. Section takes exist for auditioning and fixing; once the script reads the way they want, a Render full narration action produces the single continuous file that actually ships.

Approve on a take uploads that audio file to Cloudinary with Upload Asset, then builds a player embed pointing at the returned secure URL and writes it into the post with WordPress Update a Post, placed at the very top of the content so readers meet a play button before they start reading. Wrap the embed in a recognisable container so that approving a second take replaces the existing player instead of stacking another one on top. Record the approval in the post's history: voice, model, script version, hosted URL, who approved it, and when. That history is what powers the badge back on the queue.

A few integration details worth getting right. Deepgram authenticates with an Authorization header using the literal word Token rather than Bearer, and a Bearer prefix will fail with a 401. The speak endpoint accepts either plain text or a JSON body, and voice, model, and encoding are all query string parameters. It responds with raw audio bytes rather than JSON, with the response Content-Type matching the requested encoding and defaulting to mp3, so handle and store the response as binary rather than stuffing base64 into a record. On the Cloudinary side, audio uploads go up under the video or raw resource type. WordPress post bodies are HTML, which is why the script needs cleaning before narration and why the player goes back in as an HTML block.

Related prompts

Explore more prompts
Call overdue Xero customers with an AI collections agentShoppable link console for your WordPress recipe archiveContent decay review board for your WordPress pagesTranslation coverage grid for your published WordPress postsContent audit and refresh desk for your marketing siteWeekly sales call coaching board with rubric scorecardsInterview debrief desk that gets feedback written the same daySelf-serve brand asset portal for your Cloudinary libraryLet your content team refresh live pages without a Cloudflare loginQuarterly Cloudinary cleanup console for storage and costs