# Events Scraper – Eventbrite, Meetup & Luma (All-in-One) (`kirozhang/eventbrite-meetup-luma-events-scraper`) Actor

Search events on Eventbrite, Meetup and Luma in one run by city, keyword and date. One normalized dataset: local time & time zone, venue, address, coordinates, price, organizer, attendee count. Cross-site duplicates merged.

- **URL**: https://apify.com/kirozhang/eventbrite-meetup-luma-events-scraper.md
- **Developed by:** [Kiro Zhang](https://apify.com/kirozhang) (community)
- **Categories:** Travel, Lead generation, Automation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.00 / 1,000 events

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

### What does Events Scraper do?

This Actor searches **events on [Eventbrite](https://www.eventbrite.com), [Meetup](https://www.meetup.com) and [Luma](https://luma.com) in one run** — by **city, keyword and date** — and returns **one clean, normalized dataset**. No more running three different scrapers and merging three different formats.

Every row contains:

- 📅 **When:** start and end in UTC **and** local time, plus the time zone.
- 📍 **Where:** venue name, full address, city, region, country, postal code, **latitude / longitude** and distance from your search location. Online events are flagged.
- 🎟️ **Tickets:** free or paid, min / max price and currency, sold-out flag (Eventbrite, Luma).
- 👥 **Who & how big:** organizer (group, company or calendar) with link, attendee / RSVP count (Meetup, Luma).
- 📝 **What:** title, summary, full description, categories, cover image and event URL.
- 🔁 **Cross-site duplicates merged:** when the same event is listed on several sites you get one row with `alsoListedOn` links.

Export to JSON, CSV or Excel, call it via API, schedule it daily, or plug it into Make, Zapier, n8n, Google Sheets or an AI agent.

### Why use this events scraper?

- 🌐 **Three sites, one schema** — Eventbrite (ticketed events, conferences), Meetup (communities and groups) and Luma (tech, startup and AI events) side by side.
- 🗺️ **Works with plain city names** — `San Francisco`, `Austin, TX`, `London`, `Berlin`, `Singapore`, or `Online`. Radius in km.
- 🔎 **Keyword search with smart filtering** — Eventbrite pads thin searches with unrelated popular events; the default *smart* mode removes them.
- 💸 **Cheap, pay per event** — no monthly rental.
- ⚡ **Fast and light** — no browser, no login. ~100 events from three sites in under a minute.

#### Use cases

- **Event discovery & newsletters** — "AI events in London this week", "free tech meetups in Austin".
- **Sales & partnerships** — find conferences, meetups and organizers in your niche and city.
- **Market research** — how many events, at what price, in which cities, on which topics.
- **Venues, sponsors & community managers** — track competitors' events and what is trending locally.
- **Apps, calendars & AI agents** — feed fresh, geocoded events into your product or RAG pipeline.

### How to scrape Eventbrite, Meetup and Luma events

1. Click **Try for free** / **Start**.
2. Enter one or more **locations** (e.g. `San Francisco`, `New York`, `London`, `Berlin`, `Online`).
3. Optionally add **keywords** (e.g. `AI`, `startup`, `yoga`, `blockchain`). Each keyword is searched separately.
4. Pick **When** (today, tomorrow, this weekend, next 7 / 14 / 30 / 90 days, any upcoming date, or custom dates) and the **sites** you want.
5. Run. Download results as JSON, CSV, Excel, XML or HTML.

### Input example

```json
{
    "locations": ["Austin, TX", "Berlin"],
    "keywords": ["AI"],
    "sources": ["eventbrite", "meetup", "luma"],
    "dateRange": "next-14-days",
    "radiusKm": 40,
    "maxEventsPerSource": 100
}
```

### Output example

```json
{
    "source": "Luma",
    "title": "AI Safety Lunch + Coworking @ CIC",
    "url": "https://luma.com/h54z4aea",
    "startAt": "2026-10-08T08:00:00.000Z",
    "endAt": "2026-10-08T16:00:00.000Z",
    "startLocal": "2026-10-08T10:00",
    "endLocal": "2026-10-08T18:00",
    "timezone": "Europe/Berlin",
    "eventType": "in-person",
    "status": "active",
    "venueName": "CIC Berlin",
    "address": "CIC Berlin, Lohmühlenstraße 65, 12435 Berlin, Germany",
    "city": "Berlin",
    "country": "DE",
    "latitude": 52.494,
    "longitude": 13.446,
    "distanceKm": 3.9,
    "organizerName": "AI Safety Berlin",
    "organizerUrl": "https://luma.com/AISafetyBerlin",
    "isFree": true,
    "isSoldOut": false,
    "attendeeCount": 44,
    "alsoListedOn": [],
    "searchLocation": "Berlin",
    "searchKeyword": "AI"
}
```

#### Output fields

| Field | Description |
|---|---|
| `source` | Eventbrite, Meetup or Luma |
| `title`, `url`, `eventId` | Event title, link and ID on the source site |
| `startAt`, `endAt` | Start / end in UTC (ISO 8601) |
| `startLocal`, `endLocal`, `timezone` | Local start / end and IANA time zone |
| `eventType` | `in-person`, `online` or `hybrid` |
| `status` | `active`, `sold-out`, `cancelled`… |
| `venueName`, `address`, `city`, `region`, `country`, `postalCode` | Venue and address |
| `latitude`, `longitude`, `distanceKm` | Coordinates and distance from the search location |
| `organizerName`, `organizerUrl` | Organizer, group or calendar (personal hosts are not exported) |
| `isFree`, `priceMin`, `priceMax`, `currency`, `isSoldOut` | Ticket info where the site provides it |
| `attendeeCount` | RSVPs / guests (Meetup, Luma) |
| `categories`, `summary`, `description`, `imageUrl` | Content |
| `alsoListedOn` | Other sites listing the same event |
| `searchLocation`, `searchKeyword`, `scrapedAt` | Run context |

### How much does it cost to scrape events?

This Actor uses **pay per event**: **$2.00 per 1,000 events** ($0.002 per event) plus **$0.002 per run**. 1,000 events from three sites cost about $2. Platform usage is included. Set a maximum cost per run in the run options if you want a hard cap.

### Tips & limits

- **Eventbrite** returns up to ~1,000 events per location & keyword. Use several keywords or shorter date ranges for more.
- **Meetup** requires a keyword for search; without keywords you get Meetup's recommended events near the location.
- **Luma** lists mainly tech, startup, AI and crypto events and is strongest in big cities.
- A country or state as location (e.g. `Germany`) automatically widens the radius to 300 km.
- Prices and attendee counts are only exported where the site shows them publicly.

### Is it legal to scrape events?

This Actor only reads **public event listings** that anyone can see without logging in. It does not export personal data about attendees, and personal Luma hosts are not exported. Make sure your use complies with the sites' terms and with data-protection laws such as GDPR. If unsure, consult a lawyer.

### FAQ & support

**Can I get events for many cities at once?** Yes — add several locations; each is searched on every selected site.

**Why are there fewer events than on the website?** Past events, events outside your radius or dates, and (in *smart* mode) Eventbrite results that don't mention your keyword are filtered out.

**Something broken or missing a field?** Open an issue on the **Issues** tab — we usually reply within a day.

# Actor input Schema

## `locations` (type: `array`):

Cities to search, e.g. "San Francisco", "Austin, TX", "London", "Berlin, Germany", "Toronto, Canada". Add "Online" for virtual events (Eventbrite + Meetup). Each location is searched on every selected site.

## `keywords` (type: `array`):

e.g. "AI", "startup", "yoga", "networking", "python". Each keyword is searched separately on every site. Leave empty to get all upcoming events in the area.

## `sources` (type: `array`):

Event sites to search. Luma has no online-events search, so it is skipped for "Online".

## `dateRange` (type: `string`):

Dates are evaluated in the local time of each location. Multi-day events that are running during the period are included.

## `startDate` (type: `string`):

Used only when "When" = Custom dates. Format YYYY-MM-DD. Empty = today.

## `endDate` (type: `string`):

Used only when "When" = Custom dates. Format YYYY-MM-DD. Empty = no end.

## `radiusKm` (type: `integer`):

In-person events farther than this from the city center are dropped (distance is saved in "distanceKm"). Country-wide locations use at least 300 km.

## `includeOnline` (type: `boolean`):

Also keep online events when searching a city. (Use the location "Online" to get only online events.)

## `keywordMatch` (type: `string`):

Smart = each site's own search, but Eventbrite results that do not mention the keyword at all are dropped (Eventbrite pads thin searches with unrelated popular events). Strict needs every word of the keyword in the title, description, tags or organizer (Luma exposes only the title and organizer, so Strict is tough on Luma).

## `sortBy` (type: `string`):

Date also makes Eventbrite return the soonest events first; relevance keeps each site's own ranking.

## `maxEventsPerSource` (type: `integer`):

Upper limit per site for each location + keyword combination. Eventbrite shows at most ~1,000 results per search.

## `maxEvents` (type: `integer`):

Upper limit for the whole run (after duplicates are merged).

## `includeDescription` (type: `boolean`):

Full description where the site provides it in search results (Meetup: full text; Eventbrite: summary). No extra cost.

## `dedupeAcrossSources` (type: `boolean`):

The same event (same title and start date) listed on several sites is saved once; the other listings are in "alsoListedOn".

## `proxyConfiguration` (type: `object`):

Not needed. If a site starts rate-limiting, the scraper switches that site to a residential proxy automatically at no extra cost to you.

## Actor input object example

```json
{
  "locations": [
    "San Francisco"
  ],
  "keywords": [
    "AI"
  ],
  "sources": [
    "eventbrite",
    "meetup",
    "luma"
  ],
  "dateRange": "next-30-days",
  "radiusKm": 40,
  "includeOnline": false,
  "keywordMatch": "smart",
  "sortBy": "date",
  "maxEventsPerSource": 50,
  "maxEvents": 1000,
  "includeDescription": true,
  "dedupeAcrossSources": true,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

## `events` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "locations": [
        "San Francisco"
    ],
    "keywords": [
        "AI"
    ],
    "sources": [
        "eventbrite",
        "meetup",
        "luma"
    ],
    "maxEventsPerSource": 50
};

// Run the Actor and wait for it to finish
const run = await client.actor("kirozhang/eventbrite-meetup-luma-events-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "locations": ["San Francisco"],
    "keywords": ["AI"],
    "sources": [
        "eventbrite",
        "meetup",
        "luma",
    ],
    "maxEventsPerSource": 50,
}

# Run the Actor and wait for it to finish
run = client.actor("kirozhang/eventbrite-meetup-luma-events-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "locations": [
    "San Francisco"
  ],
  "keywords": [
    "AI"
  ],
  "sources": [
    "eventbrite",
    "meetup",
    "luma"
  ],
  "maxEventsPerSource": 50
}' |
apify call kirozhang/eventbrite-meetup-luma-events-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,kirozhang/eventbrite-meetup-luma-events-scraper"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/4gdGexYIzjW5RwELZ/builds/2u2uvgqBY2wfCJThh/openapi.json
