About

A community-built weekly schedule for X audio Spaces, with automatic local timezone conversion. Hosted at spaces.martyearthy.com Β· Created by @MartyEarthy Β· MIT licensed β€” Tesla, X, and friends are welcome to reuse it.


Reading the schedule

Each row shows a day's host. The time on the left (in blue) is your local time; hover or tap the small β“˜ info icon beside it to see the host's original scheduled time. If your local day differs from the scheduled day (e.g. you're viewing a Monday Space from a timezone where it falls on Tuesday), a small note appears next to the day name.

Status badges

A banner at the top of the page highlights any live or upcoming Space.

Live status features

What the X API cannot tell us: who is just listening to a Space (no public endpoint exists for that). The Spaces Dashboard icon on each chip links to a third-party tool that surfaces that info via scraping.


Multiple hosts per day

Some days have more than one host β€” they appear stacked in a single card, separated by a divider. Notes on individual hosts (like "may start late") are shown in small text below the time.

Spaces Dashboard Links

Toggle the Spaces Dashboard Links switch in the header to reveal chart icons next to each host. These link to Spaces Dashboard, a third-party tool for browsing Space recordings and statistics. The gold money-sign beside that switch is a joke tip jar.

Community resources

Between the weekly schedule and Awesome Hosts is a Community Resources & Sites strip. Order is shuffled on each page load (same idea as Awesome Hosts) so JSON order is not a ranking. Current entries: @Smokehbear β†’ SmokehBear's Den, @dallastsladavid β†’ Texas AV Tracker, @wholemars β†’ FSD Database. Add more in schedule.json communityResources[].

Suggest an addition

The in-page suggestion form is temporarily hidden while it is reworked. To propose a host or slot, message @MartyEarthy on X.


License

This project is MIT licensed. Tesla, X, and anyone else in the Spaces community can copy it, fork it, ship it, or build on it. Keep the copyright notice. That's the whole deal.

The grant covers this site's own code, markup, styles, and original assets. It does not cover X API data, host avatars, or recordings of other people's Spaces. Those stay with their owners. Third-party fonts and icons keep their own licenses. API keys and push secrets are never included; bring your own.

Run your own copy

Download the source zip. It is rebuilt on every deploy of this site, so it is the current code, not the old static snapshot. Our X API keys are not in it. You use your own bearer token from the X Developer Portal, and you pay X for Spaces/user reads. Cloudflare Pages/KV/D1 usually fit the free tier for a small fork.

Want only the weekly grid, no live badges? Skip the API and open index.html. Cards stay dark, and X charges nothing.

Want live status? Unzip, npm install, copy .dev.vars.example to .dev.vars with your bearer, then bash scripts/fork-setup.sh to create your own KV and D1. Step-by-step: FORK.md.


Editing the schedule (developers)

Open schedule.json. It has three top-level arrays:

scheduled

One object per recurring slot. Multiple entries with the same dayIndex create a grouped card.

FieldTypeRequiredDescription
daystringyes"Monday" … "Sunday"
dayIndexnumberyesJS Date.getDay(): Sun=0, Mon=1 … Sat=6
hoststringyesX handle without @
displayNamestringnoHuman name (falls back to host)
spaceTitlestringnoSpace title shown in italics
timestring|nullyes24-hr "HH:MM", or null for variable times
timezonestringyesIANA timezone, e.g. "America/Chicago"
displayTimestringyesHuman label, e.g. "11:00 AM CT" β€” cosmetic only
dashboardUrlstringnoSpaces Dashboard profile URL
subscribersOnlybooleannotrue renders the pink Sub badge
tentativebooleannotrue shows "Maybe?" in the live window
notestringnoShort note below the time; @mentions are auto-linked
reminderPostUrlstringnoOptional link to the host's reminder post on X (manual β€” not available from the Spaces API)

communities

Optional temporary panels (e.g. a welcome strip). Hosts are tracked for live/co-host/speak detection but are not added to Awesome Hosts chips. Set enabled to false (or empty the array) to take down. Visitors can Hide the panel; that preference stays in the browser only.

FieldTypeRequiredDescription
idstringyesStable id β€” used for hide preference
title / badge / introstringnoPanel copy
enabledbooleannoDefault true. false = no UI and no X tracking for these hosts
defaultVisiblebooleannoFirst-visit show/hide before the visitor toggles
hosts[]arraynoSame shape as additionalHosts (handle, optional dashboardUrl)
scheduled[]arraynoOptional mini-schedule (day, displayTime, host, spaceTitle)
links[]arraynolabel + url (e.g. @NICKIMINAJ profile β€” not API-tracked)

additionalHosts

FieldTypeRequiredDescription
handlestringyesX handle without @
dashboardUrlstringnoSpaces Dashboard profile URL

fetchAdditionalHostsFromXApi

Optional top-level boolean (default true if omitted). Set to false to stop querying the X API for handles listed only under additionalHosts (saves User Reads; chips still show from this file, without live API data). Cloudflare env FETCH_ADDITIONAL_HOSTS_FROM_X_API=false on Pages and Worker overrides this without editing JSON. Details: notes.md (β€œCost toggle”).

communityResources

Optional strip between the schedule and Awesome Hosts. Empty array (or omit) hides the section. Avatars are local files, not the X API. Display order is shuffled once per page load.

FieldTypeRequiredDescription
urlstringyesDestination (opens in a new tab)
labelstringnoName under the pfp (falls back to displayName β†’ handle)
handlestringnoX handle without @, shown muted under the label
avatarstringnoLocal image path, e.g. avatars/smokehbear.jpg
titlestringnoHover / accessibility title
descriptionstringnoShort blurb under the handle (turns the pill into a compact card)
displayNamestringnoLabel fallback

pinnedStreams

Drives header pills next to the logo. Entries with external: true use accent styling and a globe icon (third-party directory links); omit it for red broadcast-style pills pointing at X.

FieldTypeRequiredDescription
handlestringnoX handle without @ (omit for non-X external links)
displayNamestringnoLabel fallback when label isn't set
labelstringnoButton label (falls back to displayName β†’ handle)
urlstringyesDestination URL. Use x.com/{handle}/live for always-current live tab
externalbooleannotrue renders the accent directory pill (globe icon, no red pulse)
notestringnoMaintainer comment; ignored by UI

After editing schedule.json, run npm run deploy to publish both the Pages Function and Worker in lockstep. See notes.md for the full operational runbook.