This project runs a small local web server that:
- Authenticates to your Panopto tenant via OAuth (first run opens a browser)
- Fetches the same sessions you see in Panopto’s Subscriptions page
- Generates:
- A single combined RSS feed (optional):
panopto.xml - Per-folder RSS feeds:
subscriptions/.../feed.xml - A local index page (
index.html) to browse/copy feed URLs
- A single combined RSS feed (optional):
The server binds to 127.0.0.1 (localhost) only.
PanoptoRSS.py— main server + feed generatorconfig.json— settings you edit before runningrequirements.txt— Python dependenciesstart_panopto_rss.vbs— Windows launcher (optional)
- Python 3.10+
requests(seerequirements.txt)
From the project folder:
python -m venv .venvActivate it:
-
Windows
.\.venv\Scripts\activate
-
macOS/Linux
source .venv/bin/activate
Install dependencies:
pip install -r requirements.txtThe included VBS launcher looks for
.venv\Scripts\pythonw.exefirst, thenvenv\Scripts\pythonw.exe, then falls back topythonon PATH.
You need a Panopto OAuth client (Client ID + Client Secret) from your Panopto tenant/admin UI.
In your config.json, set:
serverto your tenant base URL, e.g.https://YOUR_TENANT.cloud.panopto.euclient_id/client_secretfrom Panoptoredirect_uri(default ishttp://127.0.0.1:8765/callback)
Make sure the redirect URI you put in config.json is also allowed/registered for that OAuth client.
The script reads config.json from the same folder as PanoptoRSS.py.
Key fields (matching the shipped template) :
server: Panopto tenant URL (no trailing slash recommended)client_id: OAuth client idclient_secret: OAuth client secretscope: usually"api"redirect_uri: localhost callback used during OAuth loginport: local server port for the RSS/index server (default 8080)refresh_minutes: refresh cadence used to derive defaultsmin_refresh_interval_seconds: minimum time between refreshes when refresh is triggered by viewing feeds/indexmax_results_per_page,max_items: paging/limit controls for subscription fetchsubscriptions_root_name: folder label used in generated treeoutput_root_dir: where generatedindex.html,panopto.xml, and per-folder feeds are writtendata_dir: where token/log/cache/state are storedtoken_cache,log_file,state_filename,folder_cache_filename,folder_cache_ttl_days,index_filenamerss_filename: name of the combined feed file. If you removerss_filenamefrom the config, the combined feed is disabled.
python PanoptoRSS.pyThen open:
http://127.0.0.1:PORT/index.html(PORT isconfig.json→port)
First run will open a browser window for Panopto login and authorization, then it caches tokens locally under data_dir.
Double-click:
start_panopto_rss.vbs
What the VBS does:
- If the server is already running: calls
http://127.0.0.1:PORT/refresh, then opens/index.html - If not running: starts the server, waits until
/healthresponds, calls/refresh, then opens/index.html
- Right-click
start_panopto_rss.vbs - Click Create shortcut
- Move the shortcut wherever you want (Desktop, Start Menu, etc.)
Important:
- Keep the actual
.vbsfile inside the project folder. - The shortcut can live anywhere; it will still launch the VBS from the project folder.
Optional: auto-start on login
- Put the shortcut into:
%APPDATA%\Microsoft\Windows\Start Menu\Programs\Startup
The VBS launcher tries (in order):
.venv\Scripts\pythonw.exevenv\Scripts\pythonw.exepythonfrom your PATH
So:
- If you create a venv named
.venvin the project folder, the VBS will “just work”. - If your environment folder has a different name/location, either rename it to
.venv/venv, or skip the VBS and runpython PanoptoRSS.pymanually.
Why pythonw.exe?
- It runs without opening a console window.
- If something fails, check
data_dir/panopto_rss.logand/healthfor the last error.
On first run, the script creates two folders (relative to the project folder):
-
output_root_dir(default:feeds/)index.html(the local UI)panopto.xml(combined feed, only ifrss_filenameis set)subscriptions_root_name/(default:Panopto Subscriptions/)- A nested folder tree that mirrors your Panopto folder hierarchy
- Each leaf folder contains a
feed.xml
-
data_dir(default:data/)panopto_token.json(OAuth token cache)state.json(last refresh time + folder signatures/paths)folder_cache.json(folder name/parent cache; TTL controlled byfolder_cache_ttl_days)panopto_rss.log(logs + errors)
Notes:
- Folder/file names are made Windows-safe (invalid characters replaced, trailing dots/spaces removed).
- If Panopto folder names collide after sanitizing, the script may suffix names like
_2,_3, etc. - When a folder disappears from your Subscriptions results, its generated feed folder can be deleted automatically on refresh.
Open:
http://127.0.0.1:PORT/index.html
It shows your subscription folder tree and provides “Open feed” / “Copy URL” buttons.
- Combined feed (if enabled):
http://127.0.0.1:PORT/panopto.xml - Per-folder feeds: served under:
http://127.0.0.1:PORT/subscriptions/.../feed.xml
Any RSS reader should work. (The feeds are local; they update when this server is running and refreshing.)
- Visiting
/index.html,/panopto.xml, or anything under/subscriptions/triggers a refresh only if enough time has passed (min_refresh_interval_seconds). - Calling
/refresh- i.e. “Refresh now” (button on the index page) - forces an immediate refresh regardless of the interval. - The VBS launcher always calls
/refreshafter launch (and also if already running).
There are two ways to stop the local server:
- From the index page: click Stop server (calls
/shutdown).- This triggers a graceful shutdown of the local HTTP server process.
- It does not delete any generated files;
feeds/anddata/stay on disk.
- If you started it in a terminal (Option A): press Ctrl+C in that terminal window.
To start again, run python PanoptoRSS.py or double-click start_panopto_rss.vbs.
The /shutdown endpoint returns “Shutting down” and then calls the server’s shutdown method in a background thread.
- If login breaks or tokens are stale: stop the server, delete the token cache file in
data_dir(default:data/panopto_token.json), then rerun. - If feeds aren’t reachable: check that
portinconfig.jsonmatches the URL you’re using. - If you see 404s for subscription feeds: make sure you actually have items in your Panopto Subscriptions page.