Skip to content

Making Channels

Austin Nunn edited this page Nov 10, 2026 · 2 revisions

Making Channels

Your server is running and Emby or Jellyfin can see the tuner. Now it needs channels. This page shows two ways to make them: with the dashboard, or with a short script. It also explains how new episodes get onto a channel by themselves.

A few words first

  • Pool: one symlink for every video in your library. The wrapper keeps it up to date. You don't touch it.
  • List: a folder of links that a channel plays, like Cartoons or Star Trek. Making a list never copies a video. It only makes links, so one video can be in many lists.
  • Station: a channel. It has a number, a name, and a plan for which lists play when.
  • Catalog: FieldStation42's index of every video a station can play. It's built from the station's lists.
  • Schedule: what plays at each minute of each day. FieldStation42 builds it a day at a time from the catalog.

Way 1: the dashboard

This is the easy way, and it covers most channels.

Make a list

  1. Open the dashboard (http://192.168.1.20:5004) and go to Lists & files.
  2. Create a list. Name it after the channel, for example Cartoons.
  3. On the left, find the shows you want. Tick their folders.
  4. Leave Keep folders up to date ticked. This "follows" the folders, so new episodes join the list later.
  5. Click Add to a list and pick your list.

A big add runs in the background. The top of the page shows how far along it is.

Make the station

  1. Go to Stations and click New station.
  2. Give it a name and a channel number, like Cartoons on channel 52.
  3. Lay out the week. Drag on a day to draw a time slot, then click the slot to pick which list plays. For one list all day, draw one slot per day, or use Start from to pick a template that does it for you.
  4. Choose how it plays the list: shuffle (random) or series order (episode 1, 2, 3 and so on).
  5. Turn off commercials and mid-show cards if you just want shows back to back.
  6. Save.

Saving builds the catalog and the first days of the schedule. The channel shows up on the dashboard about 8 seconds later. Emby and Jellyfin pick it up the next time they refresh the guide.

If you just want something on the air fast, an empty Stations page has a Make me a channel now button.

Keep it on the air

FieldStation42 only schedules a few days at a time. The Keep schedules going panel at the top of the Stations page adds days for you, so a channel never runs out. Leave it on.

Its days ahead setting is how far ahead it plans. The default is 7. A smaller number, like 2, gets new episodes on the air sooner (see New episodes below).

Add a guide channel

A guide channel scrolls through what's on every channel, like the old cable guide.

  1. Stations → New station.
  2. For the type, pick A scrolling guide of every channel.
  3. Pick a style, the number of hours to show, and a text size.
  4. Picture shape: pick widescreen for a modern TV. Pick Standard (4:3) for an old square TV.
  5. Save. It's on the air right away. There's nothing to build.

Add a pay-per-view channel

A pay-per-view channel is a menu of movies. You page through the posters with the remote and press Enter to watch one from the start.

  1. Stations → New station.
  2. For the type, pick Pay-per-view: pick a movie with the remote.
  3. Movies: a folder inside your media, like /mnt/media/movies. Every video in it and in the folders inside it becomes one movie.
  4. Pick a style, and how long each movie stays on screen before the next one shows.
  5. Save. There's nothing to build.

Each movie's title, year, plot and poster come from Emby or Jellyfin when it knows the movie (set MEDIA_SERVER_URL and MEDIA_SERVER_API_KEY), otherwise from the folder name, like Airplane! (1980). New movies show up within half an hour.

It only shows on a TV with a Client Mode Player. Emby and Jellyfin don't get this channel, because they can't show a menu.

Way 2: a script

The Stations page can't show every FieldStation42 feature. Some, like the block channels with bump cards, need the station's config written directly. A short Python script inside the container can do that.

The wrapper includes a small helper, console_client, that talks to FieldStation42 for you. Here's a whole channel in one script. It plays the Cartoons list all day, every day:

import sys
sys.path.insert(0, "/opt/tuner")
import console_client

name = "Cartoons"
every_hour = {str(h): {"tags": "Cartoons"} for h in range(24)}   # hours "0" to "23"

conf = {"station_conf": {
    "network_name": name,
    "channel_number": 52,
    "network_type": "standard",
    "content_dir": "catalog/by-genre",        # where lists live; "tags" are folder names inside it
    "off_air_video": "/opt/assets/test-pattern.mp4",
    "schedule_increment": 30,                 # shows start on the hour or half hour
    "break_strategy": "end",
    "commercial_free": False,
    "commercial_dir": ".commercials.off",     # no commercials
    "bump_dir": ".cards.off",                 # no bumpers
    "wrapper_no_breaks": True,                # shows run back to back
    "day_templates": {"daily": every_hour},
    "monday": "daily", "tuesday": "daily", "wednesday": "daily", "thursday": "daily",
    "friday": "daily", "saturday": "daily", "sunday": "daily",
}}

c = console_client.Console()
c.create(conf)              # save the station
c.rebuild_catalog(name)     # find every video in its lists
c.add_day(name)             # schedule the first day (the keeper adds the rest)

Save it as cartoons.py on the server and run it inside the container:

docker exec -i -w /opt/tuner station-wrapper-43 python3 -u - < cartoons.py

Then tell the guide to refresh, so Emby and Jellyfin see the new channel:

curl -s 'http://192.168.1.20:5004/xmltv.xml?refresh' > /dev/null

Other things console_client can do:

Call What it does
c.update(conf) Save changes to a station's config
c.update_catalog(name) Pick up new videos. The schedule stays the same.
c.rebuild_catalog(name) Rebuild the catalog from scratch. This also clears the schedule.
c.reset_schedule(name) Throw away the schedule (then use add_day)
c.add_day(name) Schedule one more day
c.delete(name) Remove the station

The Stations page shows script-made stations, but read-only if they use features the form doesn't know. Change those in your script instead.

A loop channel

A loop station doesn't follow a clock. It just plays a folder over and over, shuffled if you like. It's good for music videos.

conf = {"station_conf": {
    "network_name": "Music Videos",
    "channel_number": 60,
    "network_type": "loop",
    "content_dir": "catalog/by-genre/Music Videos",
    "shuffle_loop": True,
}}

Watch out: a loop station only plays the videos sitting directly in its folder. It ignores subfolders. If its folder holds only subfolders, building it fails with LiquidLoopBlock requires content. The dashboard's list feature adds folders as subfolders, so:

  • Fill a loop's folder with links to the videos themselves, not to folders.
  • Never "follow" a folder into a loop's list. New videos would land in subfolders, and the loop would never play them.
  • If you want a shuffled channel that keeps growing, make a normal station that plays one list all day in shuffle order instead. Normal stations read subfolders just fine.

New episodes

When a new episode shows up on your NAS, it reaches the channel by itself. It just takes a few steps:

  1. Pool (about every hour): the sync service adds a link for the new file.
  2. Follow (every 30 minutes): if you followed the show's folder, the new episode is linked into the channel's list.
  3. Catalog (once a day, around 4 am): channels whose lists changed get their catalog updated. The schedule isn't touched.
  4. Schedule: the keeper adds a day each morning. New days can use the new episode.

So a new episode first airs on the next day the keeper adds. With days ahead set to 2, that's about three days after it lands on the NAS. With 7, it's more than a week.

Want it sooner? On the Stations page, Update videos updates a station's catalog right away. Rebuild schedule redoes the days already planned.

A few things never update by themselves:

  • Folders you added with Keep folders up to date unticked.
  • Libraries that aren't in SYNC_INCLUDE in your compose file. The pool doesn't see them, so follow can't either.
  • Loop stations (see above).

Clone this wiki locally