Podcasts
Podcasting ships as the bundled Podcast extension: two schemas, podcast
for the show and podcast-episode for the episodes, a feed the directories
accept at an address of its own, and a podcast_feed() Twig function for
sites that want the feed on a page. Standard edition and above. There is no
admin screen for the feed itself; the collections are the editor.
0. Enable the extension
Section titled “0. Enable the extension”Go to Admin → Extensions, find Podcast, click Enable (or run
tcms extension:enable totalcms/podcast). The two schemas appear in the
schema list the moment it is on.
1. Create the two collections
Section titled “1. Create the two collections”The episodes. Create a collection from the podcast-episode schema. Call
it episodes, or anything you like. Give it a URL (for example /episodes/)
if episodes have their own pages; the feed links each episode to it.
The show. Create a collection from the podcast schema and tick Single
Object Collection in its settings. A show has exactly one record, so
opening the collection opens the record. Call the collection podcast — that
name is what the default feed address serves — and in the record pick the
Episodes Collection you just made. A show owns exactly one episodes
collection, which is what lets a site host several shows: each is its own
singleton collection naming its own episodes, and each has its own feed.
Neither collection is created for you by Setup Default Collections. That is deliberate: most sites do not have a podcast.
2. Fill in the show
Section titled “2. Fill in the show”Everything Apple requires is a required field, so the form will not let you save a show the directories would reject:
- Cover art must be square, between 1400 and 3000 pixels on a side, and a JPG or PNG. Upload the real file at that size; the feed serves it as-is.
- Categories come from Apple’s list. Choose up to three. The first one is the primary category that directories show.
- Owner email is where Apple and Spotify send ownership notices. It goes in the feed but is never shown in apps.
- Explicit must be answered either way.
The optional fields are for later: Funding adds a support link in apps that read the Podcast Index namespace, Locked tells other hosts not to import your feed, and New feed URL is only for moving.
3. Add episodes
Section titled “3. Add episodes”Each episode needs a title, a date, and its audio, which you can supply two ways:
- Upload it to the Audio File field. Total CMS hosts it, serves it
through the streaming route apps expect, and counts every listen: the
number is on the file in the admin and available in Twig as
episode.audio.count. MP3 is the safe choice; every app plays it. - Link it with the Audio URL field when the file lives on your own host or storage bucket. Fill in the file size in bytes as well, since apps use it for download progress. Linked audio is not counted by Total CMS; see Download numbers below.
If both are set, the uploaded file wins. An episode with neither is left out of the feed.
Fill in the duration in seconds if you know it, since apps use it for progress bars. Episode and season numbers, the episode type, show notes, a summary, and per-episode art are all optional. Transcripts and chapter files work the same way as audio: upload them, or link to them.
Two things keep an episode out of the feed: the Draft box, and a date in the future. Schedule an episode by dating it ahead; it appears in the feed when the date arrives.
4. Publish the feed
Section titled “4. Publish the feed”The feed is already published. The extension serves it, as application/rss+xml, at:
/api/ext/totalcms/podcast/feedThat address reads the show in the collection named podcast. Any other show
is served by its collection id at /api/ext/totalcms/podcast/feed/{show}.
Hand that address to the directories and you are done — no page, no template, and it works the same on a Stacks
site as on Site Builder. A show with no record, or one that names no episodes
collection, answers 404 with a message that says which, rather than an empty
feed the directories would reject.
If you would rather the feed live at an address of your own, render it on a
page. In Site Builder, add a page at /podcast.xml whose template is:
{{ podcast_feed() }}The argument is the show collection and defaults to podcast; the episodes
come from the show record. Options: link (your site’s home page, default
/), language (for example en-US), copyright, and self to name a
different address for one rendering. The page must be served as XML — the
router does that for a .xml route. The page’s own URL becomes the feed’s
address: apps re-fetch with it and the show’s identifier derives from it.
Either way the feed is the show’s details, the episodes newest first, an
enclosure for each audio file, and the iTunes and Podcast Index tags the
directories read. If you would rather build the feed by hand from your own
schema, Feeds shows the podcast block that this fills
in for you.
5. Validate and submit
Section titled “5. Validate and submit”Open the feed URL in a browser and check it renders as XML. Then run it through a validator such as podba.se/validate or Apple’s own checker in Podcasts Connect. A feed that renders in Total CMS has already passed the checks the writer knows about, so the validators mostly confirm the artwork dimensions and that the audio URLs are reachable.
Submit the feed URL to Apple Podcasts Connect, Spotify for Podcasters, and the Podcast Index. Most other apps read from those three.
Moving hosts or feed URLs
Section titled “Moving hosts or feed URLs”Podcast apps identify your show by a permanent GUID, which Total CMS derives
from the feed’s address — the extension’s route, or the page that renders
podcast_feed(). Moving the feed, including from the route to a page of your
own, changes that address. Before you do, copy the existing GUID from your
feed into the show’s Podcast GUID field so the identifier survives, and
set New feed URL so apps follow you. Change the GUID and every listener’s
app sees a brand-new show.
Episode IDs work the same way: the ID is the item’s identity in the feed. Change it and the episode is re-announced as new.
Large shows
Section titled “Large shows”Uploaded audio is served by Total CMS through the file field’s streaming route, which is fine for a few hundred downloads an episode. A show with real reach is better served from your own storage bucket: bandwidth stops being your web host’s problem and byte-range requests, which apps rely on for scrubbing, are handled by the bucket. Today that means uploading to the bucket yourself and using the Audio URL field. The S3 Uploads extension will make that a drag-and-drop upload that is still counted.
Download numbers
Section titled “Download numbers”Uploaded episodes are counted: every fetch through the streaming route adds
one to the file’s download count, which you can see on the file in the admin
and read in Twig as episode.audio.count. It is a plain fetch count, so it
includes validators and re-downloads; treat it as a trend, not an audit.
Linked episodes are not counted, because the audio never passes through Total CMS. Independent podcasters use a prefix analytics service in front of the audio URL instead. If you build your feed by hand from Feeds, the prefix is one string change on the enclosure URL.