Shirecal is a Val Town HTTP val that turns a JSON payload of Middle-earth events into an iCalendar (.ics) feed. The val stores events in Val Town blob storage and always serves the next upcoming instance for each event (including multi-day spans).
GET / – Returns an .ics file with the next occurrence of every stored event.GET /?format=json – Returns the currently stored events as JSON.PUT / – Replaces all stored events. Body must be JSON shaped like { "events": ShireEvent[] }.interface ShireEvent {
start: string; // MM-DD
end?: string; // MM-DD (optional)
text: string; // Narrative snippet used as the calendar description
characters: string[]; // Key figures tied to the event (e.g. ["Frodo", "Sam"])
sourceText: string; // e.g. "The Two Towers"
sourceChapter: string; // e.g. "The Forbidden Pool"
sourceMovie?: string; // e.g. "The Two Towers (Extended Edition)"
sourceTimestamp?: string; // HH:MM:SS within the chosen cut
location: string; // Where the scene happens (best-effort label)
}
start and end are month/day strings (MM-DD).end blank for single-day events.end is earlier than start (e.g. 12-29 to 01-02), the event wraps into the next year automatically.characters drives the calendar event summary (Gandalf's Journey, Frodo & Sam, etc.). Include the central figures mentioned in the narrative.sourceText and sourceChapter annotate where the moment appears in Tolkien's canon so subscribers can trace the scene.sourceMovie / sourceTimestamp (optional) point to the film adaptation and timestamp; use Not in film when the scene never made it to the screen.location keeps a concise label for the place; we surface it inside the event body and set the ICS LOCATION property.