Skip to main content
Glama

SFomo: Bay Area events

List upcoming events

list_upcoming
Read-onlyIdempotent

Browse the next N days of events day by day, with no search words. by_day counts every match per date, and when more events match than limit the rows are spread evenly across the days (earliest first within each day), so each day is represented. Use it for overviews like "what's happening this week"; for search words, free-only, a town or exact from/to dates use search_events, and for one event's details get_event. Optional filters: one category or topic, an audience, and a place: neighborhood keeps events inside a named area (radius_km widens it past the boundary), near ranks events by distance from a place or "lat,lon" within radius_km. No sign-in; each client gets 30 calls a minute and 2,500 event rows an hour.

Input Schema

NameRequiredDescriptionDefault
daysNoWindow in days (default 7, max 60)
nearNoEvents within radius_km of a place: a neighborhood, a town, a venue name, or "lat,lon". Results get distance_km, nearest first within each day. Use this for "near X"; use neighborhood for "in X". Unmapped venues are left out (counted in place.unplaced_events).
limitNoMax rows (default 50, max 100)
topicNo
sectorNoIndustry a work event is for (only events with a work topic carry one; general networking has none): e.g. senior_care, healthcare, real_estate, finance_insurance, legal, tech
audienceNoWho the event is only for: kids, teens, seniors (older adults: senior-center programs, 55+ groups), or general (none of those). Default: no filter. Caregiver/aging talks for families and professionals are general.
categoryNo
radius_kmNoDistance for near (default 1.5, max 50), or how far neighborhood reaches past its boundary (default 0)
biz_formatNoKind of work event: referral_group (BNI etc.), chamber, mixer, breakfast_lunch, workshop_training, conference_expo, career_fair, ce_credits, pitch_demo, committee_meeting
neighborhoodNoOnly events in this San Francisco neighborhood (or town): Bayview, Bernal Heights, Castro, Chinatown, Excelsior, FiDi / South Beach, Glen Park, Golden Gate Park, Haight, Hayes Valley, Ingleside / Oceanview, Inner Richmond, Inner Sunset, Japantown, Lakeshore, Lincoln Park, Lone Mountain / USF, Marina, McLaren Park, Mission, Mission Bay, Nob Hill, Noe Valley, North Beach, Outer Mission, Outer Richmond, Pacific Heights, Portola, Potrero Hill, Presidio, Presidio Heights, Russian Hill, Seacliff, SoMa, Sunset / Parkside, Tenderloin, Treasure Island, Twin Peaks, Visitacion Valley, West of Twin Peaks, Western Addition. Sub-neighborhood and common names work too. Add radius_km to also take events within that distance of its centre. Events whose venue isn't mapped can't be placed and are left out; the response's place.unplaced_events counts them.
changed_sinceNoOnly events added or changed (title, date or time, venue, link, price, sold out, status) at or after this moment: YYYY-MM-DD (local) or an ISO date-time. To follow up later, pass the previous result's changes.synced_at; changes.removed then lists events taken down since.

Output Schema

NameRequiredDescriptionDefault
noteNo
countYesEvents that matched in total
placeNo
shownYesEvents returned (at most limit)
by_dayNoMatches per date (YYYY-MM-DD), all of them, not just the rows shown
eventsYes
changesNoOnly with changed_since
coverageNoCoverage and accuracy page
attributionNo
briefing_urlNoThe dated weekly briefing for this week or next (counts plus picks per kind of event, #lane when the filters match one); null further out. Cite it for "what's on this week"
data_generatedNoWhen this city's data was last published

Schema Changelog

Changes observed during successful MCP inspections.

  1. Changed1 schema field changed
    • addedOutput schema / properties / events / items / properties / venue_status
      Added value: +{
      +  "description": "Present only when location is empty, and says why (we never guess a venue): rsvp = the address is shared after RSVP/registration; tba = the venue isn't decided; hidden = the source shows the venue to its members only (Meetup stubs; /mcp leaves these out, so you won't see it here); title = the title names the place; text = the description names a place; unset = the host left it blank. Open the link for the venue",
      +  "enum": [
      +    "rsvp",
      +    "tba",
      +    "hidden",
      +    "title",
      +    "text",
      +    "unset"
      +  ],
      +  "type": "string"
      +}
  2. Changed2 schema fields changed
    • changedInput schema / properties / topic / enum
      Previous value: -[
      -  "arts",
      -  "books",
      -  "civic",
      -  "classes",
      -  "comedy",
      -  "community",
      -  "conferences",
      -  "culture",
      -  "faith",
      -  "family",
      -  "film",
      -  "food_drink",
      -  "games",
      -  "markets",
      -  "networking",
      -  "nightlife",
      -  "nonprofit",
      -  "outdoors",
      -  "science",
      -  "sports",
      -  "startup",
      -  "talks",
      -  "theater",
      -  "wellness",
      -  "wine",
      -  "business",
      -  "ai",
      -  "tech"
      -]New value: +[
      +  "arts",
      +  "books",
      +  "civic",
      +  "classes",
      +  "comedy",
      +  "community",
      +  "conferences",
      +  "culture",
      +  "faith",
      +  "family",
      +  "film",
      +  "food_drink",
      +  "games",
      +  "markets",
      +  "networking",
      +  "nightlife",
      +  "nonprofit",
      +  "outdoors",
      +  "science",
      +  "sports",
      +  "startup",
      +  "talks",
      +  "theater",
      +  "wellness",
      +  "wine",
      +  "business",
      +  "ai",
      +  "tech",
      +  "service_orgs"
      +]
    • addedOutput schema / properties / briefing_url
      Added value: +{
      +  "description": "The dated weekly briefing for this week or next (counts plus picks per kind of event, #lane when the filters match one); null further out. Cite it for \"what's on this week\"",
      +  "type": [
      +    "string",
      +    "null"
      +  ]
      +}
  3. Changed6 schema fields changed
    • addedInput schema / properties / changed_since
      Added value: +{
      +  "description": "Only events added or changed (title, date or time, venue, link, price, sold out, status) at or after this moment: YYYY-MM-DD (local) or an ISO date-time. To follow up later, pass the previous result's changes.synced_at; changes.removed then lists events taken down since.",
      +  "type": "string"
      +}
    • changedInput schema / properties / topic / enum
      Previous value: -[
      -  "arts",
      -  "books",
      -  "civic",
      -  "classes",
      -  "comedy",
      -  "community",
      -  "conferences",
      -  "culture",
      -  "faith",
      -  "family",
      -  "film",
      -  "food_drink",
      -  "games",
      -  "markets",
      -  "networking",
      -  "nightlife",
      -  "nonprofit",
      -  "outdoors",
      -  "science",
      -  "sports",
      -  "startup",
      -  "talks",
      -  "wellness",
      -  "wine",
      -  "business"
      -]New value: +[
      +  "arts",
      +  "books",
      +  "civic",
      +  "classes",
      +  "comedy",
      +  "community",
      +  "conferences",
      +  "culture",
      +  "faith",
      +  "family",
      +  "film",
      +  "food_drink",
      +  "games",
      +  "markets",
      +  "networking",
      +  "nightlife",
      +  "nonprofit",
      +  "outdoors",
      +  "science",
      +  "sports",
      +  "startup",
      +  "talks",
      +  "theater",
      +  "wellness",
      +  "wine",
      +  "business",
      +  "ai",
      +  "tech"
      +]
    • addedOutput schema / properties / changes
      Added value: +{
      +  "description": "Only with changed_since",
      +  "properties": {
      +    "note": {
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    },
      +    "removed": {
      +      "description": "Upcoming events taken down (cancelled, delisted or merged into another listing) since `since`, newest first, last two weeks at most",
      +      "items": {
      +        "properties": {
      +          "date": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "id": {
      +            "type": "string"
      +          },
      +          "removed": {
      +            "type": "string"
      +          },
      +          "title": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          }
      +        },
      +        "required": [
      +          "id",
      +          "removed"
      +        ],
      +        "type": "object"
      +      },
      +      "type": "array"
      +    },
      +    "removed_count": {
      +      "description": "Total removals when more than are listed",
      +      "type": "number"
      +    },
      +    "since": {
      +      "type": "string"
      +    },
      +    "synced_at": {
      +      "description": "Pass this as changed_since next time to get only what changed after this answer",
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    },
      +    "tracked_since": {
      +      "description": "When change tracking started for this city",
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    }
      +  },
      +  "required": [
      +    "since",
      +    "removed"
      +  ],
      +  "type": "object"
      +}
    • addedOutput schema / properties / events / items / properties / changed
      Added value: +{
      +  "description": "When we last saw the title, date or time, venue, link, price or status change (local ISO time); the first-seen day for older events",
      +  "type": [
      +    "string",
      +    "null"
      +  ]
      +}
    • addedOutput schema / properties / events / items / properties / event_status
      Added value: +{
      +  "description": "What a source says: postponed (no new date yet; listed on its original date), rescheduled (this is the new date), moved (to another venue; location is the new one), sold_out. Absent = scheduled as listed; cancelled events are left out",
      +  "enum": [
      +    "sold_out",
      +    "postponed",
      +    "rescheduled",
      +    "moved"
      +  ],
      +  "type": "string"
      +}
    • addedOutput schema / properties / events / items / properties / status_note
      Added value: +{
      +  "description": "The source's own wording of event_status, e.g. \"Moved to The Warfield\"",
      +  "type": "string"
      +}
  4. Changed1 schema field changed
    • addedOutput schema / properties / events / items / properties / checked_live
      Added value: +{
      +  "description": "When we last opened the original listing and found it still matches (time, venue, not cancelled); local ISO time. Absent = not checked in the last two days",
      +  "type": [
      +    "string",
      +    "null"
      +  ]
      +}
  5. Changed5 schema fields changed
    • addedInput schema / properties / audience
      Added value: +{
      +  "description": "Who the event is only for: kids, teens, seniors (older adults: senior-center programs, 55+ groups), or general (none of those). Default: no filter. Caregiver/aging talks for families and professionals are general.",
      +  "enum": [
      +    "general",
      +    "kids",
      +    "teens",
      +    "seniors"
      +  ],
      +  "type": "string"
      +}
    • addedInput schema / properties / biz_format
      Added value: +{
      +  "description": "Kind of work event: referral_group (BNI etc.), chamber, mixer, breakfast_lunch, workshop_training, conference_expo, career_fair, ce_credits, pitch_demo, committee_meeting",
      +  "enum": [
      +    "referral_group",
      +    "chamber",
      +    "mixer",
      +    "breakfast_lunch",
      +    "workshop_training",
      +    "conference_expo",
      +    "career_fair",
      +    "ce_credits",
      +    "pitch_demo",
      +    "committee_meeting"
      +  ],
      +  "type": "string"
      +}
    • addedInput schema / properties / sector
      Added value: +{
      +  "description": "Industry a work event is for (only events with a work topic carry one; general networking has none): e.g. senior_care, healthcare, real_estate, finance_insurance, legal, tech",
      +  "enum": [
      +    "senior_care",
      +    "healthcare",
      +    "life_sciences",
      +    "real_estate",
      +    "finance_insurance",
      +    "legal",
      +    "tech",
      +    "defense_government",
      +    "trades_construction",
      +    "hospitality_food",
      +    "retail_ecommerce",
      +    "marketing_media",
      +    "nonprofit",
      +    "energy_climate",
      +    "hr_workforce",
      +    "creative_design"
      +  ],
      +  "type": "string"
      +}
    • changedInput schema / properties / topic / enum
      Previous value: -[
      -  "arts",
      -  "books",
      -  "civic",
      -  "classes",
      -  "comedy",
      -  "community",
      -  "conferences",
      -  "culture",
      -  "faith",
      -  "family",
      -  "film",
      -  "food_drink",
      -  "games",
      -  "markets",
      -  "networking",
      -  "nightlife",
      -  "nonprofit",
      -  "outdoors",
      -  "science",
      -  "sports",
      -  "startup",
      -  "talks",
      -  "wellness",
      -  "wine"
      -]New value: +[
      +  "arts",
      +  "books",
      +  "civic",
      +  "classes",
      +  "comedy",
      +  "community",
      +  "conferences",
      +  "culture",
      +  "faith",
      +  "family",
      +  "film",
      +  "food_drink",
      +  "games",
      +  "markets",
      +  "networking",
      +  "nightlife",
      +  "nonprofit",
      +  "outdoors",
      +  "science",
      +  "sports",
      +  "startup",
      +  "talks",
      +  "wellness",
      +  "wine",
      +  "business"
      +]
    • changedOutput schema / (root)
      Previous value: -nullNew value: +{
      +  "properties": {
      +    "attribution": {
      +      "type": "string"
      +    },
      +    "by_day": {
      +      "additionalProperties": {
      +        "type": "number"
      +      },
      +      "description": "Matches per date (YYYY-MM-DD), all of them, not just the rows shown",
      +      "type": "object"
      +    },
      +    "count": {
      +      "description": "Events that matched in total",
      +      "type": "number"
      +    },
      +    "coverage": {
      +      "description": "Coverage and accuracy page",
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    },
      +    "data_generated": {
      +      "description": "When this city's data was last published",
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    },
      +    "events": {
      +      "items": {
      +        "properties": {
      +          "audience": {
      +            "description": "kids, teens or seniors when the event is only for them",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "biz_formats": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          },
      +          "categories": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          },
      +          "city": {
      +            "description": "Town or city within the metro",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "date": {
      +            "description": "Local start date, YYYY-MM-DD",
      +            "type": "string"
      +          },
      +          "distance_km": {
      +            "description": "With near: distance from the place",
      +            "type": "number"
      +          },
      +          "end": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "first_seen": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "free": {
      +            "type": "boolean"
      +          },
      +          "id": {
      +            "description": "Stable 12-character id; pass it to get_event",
      +            "type": "string"
      +          },
      +          "last_fetched": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "last_seen": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "link": {
      +            "description": "The original listing; keep it and credit What's Up In",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "location": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "neighborhood": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "performers": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          },
      +          "possibly_free": {
      +            "type": "boolean"
      +          },
      +          "posted_by_sources": {
      +            "type": "number"
      +          },
      +          "price": {
      +            "description": "All-in price as the source states it, \"Free\", or \"See tickets\" when the source doesn't state the all-in total",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "recurring": {
      +            "description": "weekly, biweekly or monthly when the event is one date of a series",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "region": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "rv": {
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "sectors": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          },
      +          "sold_out": {
      +            "type": "boolean"
      +          },
      +          "sources": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          },
      +          "start": {
      +            "description": "Local start, ISO 8601, when the source gives a time",
      +            "type": [
      +              "string",
      +              "null"
      +            ]
      +          },
      +          "title": {
      +            "type": "string"
      +          },
      +          "topics": {
      +            "items": {
      +              "type": "string"
      +            },
      +            "type": "array"
      +          }
      +        },
      +        "required": [
      +          "id",
      +          "title",
      +          "date"
      +        ],
      +        "type": "object"
      +      },
      +      "type": "array"
      +    },
      +    "note": {
      +      "type": [
      +        "string",
      +        "null"
      +      ]
      +    },
      +    "place": {
      +      "properties": {
      +        "center": {
      +          "items": {
      +            "type": "number"
      +          },
      +          "type": "array"
      +        },
      +        "kind": {
      +          "type": [
      +            "string",
      +            "null"
      +          ]
      +        },
      +        "matched": {
      +          "type": [
      +            "string",
      +            "null"
      +          ]
      +        },
      +        "note": {
      +          "type": [
      +            "string",
      +            "null"
      +          ]
      +        },
      +        "radius_km": {
      +          "type": [
      +            "number",
      +            "null"
      +          ]
      +        },
      +        "unplaced_events": {
      +          "description": "Events left out because their venue isn't mapped",
      +          "type": "number"
      +        }
      +      },
      +      "required": [],
      +      "type": "object"
      +    },
      +    "shown": {
      +      "description": "Events returned (at most limit)",
      +      "type": "number"
      +    }
      +  },
      +  "required": [
      +    "count",
      +    "shown",
      +    "events"
      +  ],
      +  "type": "object"
      +}
  6. Changed4 schema fields changed
    • addedInput schema / properties / limit
      Added value: +{
      +  "description": "Max rows (default 50, max 100)",
      +  "type": "integer"
      +}
    • addedInput schema / properties / near
      Added value: +{
      +  "description": "Events within radius_km of a place: a neighborhood, a town, a venue name, or \"lat,lon\". Results get distance_km, nearest first within each day. Use this for \"near X\"; use neighborhood for \"in X\". Unmapped venues are left out (counted in place.unplaced_events).",
      +  "type": "string"
      +}
    • addedInput schema / properties / neighborhood
      Added value: +{
      +  "description": "Only events in this San Francisco neighborhood (or town): Bayview, Bernal Heights, Castro, Chinatown, Excelsior, FiDi / South Beach, Glen Park, Golden Gate Park, Haight, Hayes Valley, Ingleside / Oceanview, Inner Richmond, Inner Sunset, Japantown, Lakeshore, Lincoln Park, Lone Mountain / USF, Marina, McLaren Park, Mission, Mission Bay, Nob Hill, Noe Valley, North Beach, Outer Mission, Outer Richmond, Pacific Heights, Portola, Potrero Hill, Presidio, Presidio Heights, Russian Hill, Seacliff, SoMa, Sunset / Parkside, Tenderloin, Treasure Island, Twin Peaks, Visitacion Valley, West of Twin Peaks, Western Addition. Sub-neighborhood and common names work too. Add radius_km to also take events within that distance of its centre. Events whose venue isn't mapped can't be placed and are left out; the response's place.unplaced_events counts them.",
      +  "type": "string"
      +}
    • addedInput schema / properties / radius_km
      Added value: +{
      +  "description": "Distance for near (default 1.5, max 50), or how far neighborhood reaches past its boundary (default 0)",
      +  "type": "number"
      +}
  7. Changed1 schema field changed
    • changedInput schema / properties / topic / enum
      Previous value: -[
      -  "arts",
      -  "books",
      -  "civic",
      -  "classes",
      -  "comedy",
      -  "community",
      -  "conferences",
      -  "culture",
      -  "faith",
      -  "family",
      -  "film",
      -  "food_drink",
      -  "games",
      -  "markets",
      -  "networking",
      -  "nightlife",
      -  "nonprofit",
      -  "outdoors",
      -  "science",
      -  "sports",
      -  "startup",
      -  "talks",
      -  "wellness"
      -]New value: +[
      +  "arts",
      +  "books",
      +  "civic",
      +  "classes",
      +  "comedy",
      +  "community",
      +  "conferences",
      +  "culture",
      +  "faith",
      +  "family",
      +  "film",
      +  "food_drink",
      +  "games",
      +  "markets",
      +  "networking",
      +  "nightlife",
      +  "nonprofit",
      +  "outdoors",
      +  "science",
      +  "sports",
      +  "startup",
      +  "talks",
      +  "wellness",
      +  "wine"
      +]
  8. First observed

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnly/idempotent/non-destructive, but the description adds behavior the annotations cannot: no sign-in required, a concrete rate budget (30 calls/minute, 2,500 event rows/hour), and the non-obvious result-shaping rule that rows are spread evenly across days when matches exceed limit. It also discloses the failure mode that unmapped venues are dropped and counted in place.unplaced_events.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded with the core browse behavior and the by_day spreading rule, then the routing to siblings, then filters, then the access/rate note. Dense but nearly every sentence carries new information; the filter enumeration repeats ground the schema already covers.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With 11 params, an output schema, and rich annotations, the description supplies what structured fields can't: rate limits, the even-spread semantics, and sibling routing. It stops short of explaining the interplay among all filters (e.g. combining neighborhood with topic or using changed_since for follow-up polling), which the schema carries alone.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 82%, so the schema already does most of the work, but the description adds the key disambiguation an agent would otherwise miss: 'near' ranks by distance while 'neighborhood' restricts to an area, and radius_km means different things depending on which one is used. The summary of optional filters omits sector, biz_format, and changed_since, leaving those to the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('Browse the next N days of events day by day, with no search words') and immediately distinguishes itself from search_events and get_event by name. An agent can identify this as the browse-by-date-window tool without opening any schema.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Gives an explicit positive case ('overviews like what's happening this week') and explicit negative cases routed to alternatives: search words, free-only, a town or exact from/to dates go to search_events, single-event details go to get_event. Both sides of the use/don't-use decision are covered.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Try in Browser

Glama MCP Gateway

Add one secure layer between your agents and this server.

Resources