# GFAVIP Tickets API

> Supported public and integration APIs for GFAVIP Tickets

GFAVIP Tickets provides event discovery, ticket registration, attendee-directory preferences, Community Interest embeds, and authorized event operations. This document is the canonical source for the public integration contract. Internal administration routes not listed here are not a supported external API.

Version: `2026-07-22`

Base URL: `https://tickets.gfavip.com`

## Machine-readable entry points

- [OpenAPI 3.1 JSON](https://tickets.gfavip.com/openapi.json)
- [Markdown API reference](https://tickets.gfavip.com/docs.md)
- [Complete LLM reference](https://tickets.gfavip.com/llms-full.txt)
- [Agent event-management skill](https://tickets.gfavip.com/skill.md)
- [Short LLM discovery index](https://tickets.gfavip.com/llms.txt)

## Authentication

- Public event and embed endpoints require no authentication.
- Browser users authenticate through GFAVIP SSO and receive a secure session cookie.
- Headless agents send `Authorization: Bearer <GFAVIP_TOKEN>` and must follow the authorization and audit rules in `skill.md`.
- Tokens are secrets. Never put them in URLs, event data, logs, examples, or chat messages.

## Quick start

```bash
curl --fail --silent --show-error https://tickets.gfavip.com/api/events
```

```javascript
const response = await fetch('https://tickets.gfavip.com/api/events');
if (!response.ok) throw new Error(`Tickets API returned ${response.status}`);
const events = await response.json();
```

```python
import requests

response = requests.get('https://tickets.gfavip.com/api/events', timeout=10)
response.raise_for_status()
events = response.json()
```

Event permalinks use the numeric event ID: `https://tickets.gfavip.com/events/{id}`. Do not treat the optional slug as the public event permalink.

For `imageUrl`, use an existing absolute URL as-is. For a storage identifier, construct `https://tickets.gfavip.com/event-images/{imageUrl}`. Use a placeholder when the value is null.

## Events

Anonymous event discovery.

### `GET /api/events`

**List active events**

Returns active public events. Internal ownership, assigned-partner, revenue-share, private-note, and Community Interest estimate fields are removed by the server.

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `type` | query | no | EventType | Filter by event type. |

Responses:

- **200** — Active events (`array of PublicEvent`)
- **500** — Unexpected server error (`Error`)

### `GET /api/events/{id}`

**Get one event**

Returns one public event by numeric ID. Cancelled events may still be returned so clients can display their status.

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `id` | path | yes | integer | Numeric event ID. |

Responses:

- **200** — Public event (`PublicEvent`)
- **404** — Resource not found (`Error`)
- **500** — Unexpected server error (`Error`)

### `GET /api/events/{id}/side-events`

**List side events**

Returns public child events for a parent event. The same public-field filter used by the main event endpoints is applied.

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `id` | path | yes | integer | Numeric event ID. |

Responses:

- **200** — Side events (`array of PublicEvent`)
- **500** — Unexpected server error (`Error`)

### `GET /api/events/{id}/promotional-materials`

**List event promotional materials**

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `id` | path | yes | integer | Numeric event ID. |

Responses:

- **200** — Promotional materials (`array of PromotionalMaterial`)

## Embeds

Anonymous partner-site embed data.

### `GET /api/public/events/{slug}/fomo`

**Get public capacity and social-proof data**

CORS-enabled endpoint for partner-site embeds. Community Interest is returned only when enabled for the event.

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `slug` | path | yes | string | Event slug used by embed endpoints. |

Responses:

- **200** — FOMO data (`FomoResponse`)
- **404** — Resource not found (`Error`)

### `GET /api/public/events/{slug}/tiers`

**Get public ticket tiers**

CORS-enabled endpoint. Hidden and member-only tiers are excluded.

Authentication: none

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `slug` | path | yes | string | Event slug used by embed endpoints. |

Responses:

- **200** — Public ticket tiers (`PublicTierResponse`)
- **404** — Resource not found (`Error`)

## Account

Authenticated account preferences.

### `GET /api/auth/user`

**Get the browser-session user**

Returns the current browser-session user or null. Headless agents should verify access with an authorized endpoint such as GET /api/admin/events instead.

Authentication: none

Responses:

- **200** — Session user or null (`SessionUser or null`)

### `GET /api/account/attendee-directory-preference`

**Get the account-wide directory preference**

Authentication: `cookieAuth` or `bearerAuth`

Responses:

- **200** — Current preference (`BooleanPreference`)
- **401** — Authentication required (`Error`)

### `PATCH /api/account/attendee-directory-preference`

**Update the account-wide directory preference**

Opting out removes the user from all attendee directories immediately. It does not prevent a confirmed attendee from viewing an enabled directory.

Authentication: `cookieAuth` or `bearerAuth`

Request body:

```json
{
  "$ref": "#/components/schemas/BooleanPreference"
}
```

Responses:

- **200** — Updated preference (`BooleanPreference`)
- **400** — Invalid request (`Error`)
- **401** — Authentication required (`Error`)

## Tickets

Authenticated registration and ticket access.

### `GET /api/tickets`

**List the authenticated user's tickets**

Authentication: `cookieAuth` or `bearerAuth`

Responses:

- **200** — Tickets (`array of Ticket`)
- **401** — Authentication required (`Error`)

### `GET /api/tickets/check-eligibility/{eventId}`

**Check registration eligibility**

Authentication: `cookieAuth` or `bearerAuth`

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `eventId` | path | yes | integer |  |

Responses:

- **200** — Eligibility decision (`object`)
- **401** — Authentication required (`Error`)

### `POST /api/tickets/apply`

**Apply for an event ticket**

Creates a ticket application. A pending application is not a confirmed attendee and does not grant directory access.

Authentication: `cookieAuth` or `bearerAuth`

Request body:

```json
{
  "type": "object",
  "required": [
    "eventId",
    "applicationData"
  ],
  "properties": {
    "eventId": {
      "type": "integer"
    },
    "applicationData": {
      "type": "object",
      "additionalProperties": true
    },
    "useGems": {
      "type": "boolean",
      "default": false
    },
    "ticketTier": {
      "type": "string"
    }
  },
  "additionalProperties": false
}
```

Responses:

- **200** — Created ticket and application (`object`)
- **400** — Invalid request (`Error`)
- **401** — Authentication required (`Error`)

## Attendee Directory

Privacy-gated attendee discovery.

### `GET /api/events/{id}/attendee-directory`

**Get an event's attendee directory**

The viewer must hold a paid or checked-in ticket and the event team must have enabled the directory. Only confirmed attendees who opted in appear. Contact and ticket data are never returned.

Authentication: `cookieAuth` or `bearerAuth`

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `id` | path | yes | integer | Numeric event ID. |

Responses:

- **200** — Directory state and sanitized public profiles (`AttendeeDirectoryResponse`)
- **401** — Authentication required (`Error`)
- **404** — Resource not found (`Error`)

## Event Operations

Authorized event-team operations.

### `GET /api/admin/events/{eventId}/community-features`

**Get directory and Community Interest settings**

Admins and staff can access all events according to their role. Partners and event agents are limited to owned or assigned events.

Authentication: `cookieAuth` or `bearerAuth`

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `eventId` | path | yes | integer |  |

Responses:

- **200** — Community feature settings and counts (`CommunityFeatureSettings`)
- **401** — Authentication required (`Error`)
- **403** — The authenticated user lacks permission (`Error`)

### `PATCH /api/admin/events/{eventId}/community-features`

**Update directory or Community Interest settings**

Staff may update Community Interest but not the directory. Event-agent bearer requests must include X-Action-Reason.

Authentication: `cookieAuth` or `bearerAuth`

| Parameter | Location | Required | Type | Description |
|---|---|---:|---|---|
| `eventId` | path | yes | integer |  |
| `X-Action-Reason` | header | no | string | Required for event-agent bearer updates. |

Request body:

```json
{
  "type": "object",
  "minProperties": 1,
  "properties": {
    "attendeeDirectoryEnabled": {
      "type": "boolean"
    },
    "communityInterestEnabled": {
      "type": "boolean"
    },
    "communityInterestEstimate": {
      "type": "integer",
      "minimum": 0,
      "maximum": 1000000
    }
  },
  "additionalProperties": false
}
```

Responses:

- **200** — Settings updated
- **400** — Invalid request (`Error`)
- **401** — Authentication required (`Error`)
- **403** — The authenticated user lacks permission (`Error`)

## Public data guarantees

- Public event responses never contain `createdBy`, `assignedPartners`, `revenueShares`, `privateNotes`, or the internal Community Interest estimate.
- Attendee-directory responses contain only sanitized public profile fields and never contain email addresses, telephone numbers, ticket details, payment data, or check-in state.
- Community Interest is an aggregate marketing signal and never creates a ticket, reserves capacity, or grants event access.

## Human integration guides

- [Simple SSO](https://tickets.gfavip.com/docs/simple-sso) — Browser SSO guidance for GFAVIP mini apps.
- [FOMO and Ticket Embeds](https://tickets.gfavip.com/docs/fomo-tier-embed) — Partner-site embed widgets and customization.
- [Roles and Permissions](https://tickets.gfavip.com/docs/roles) — Human-readable role overview.

## Schemas

### EventType

```json
{
  "type": "string",
  "enum": [
    "cbs",
    "meetup",
    "webinar",
    "partner",
    "virtual"
  ]
}
```

### PublicEvent

```json
{
  "type": "object",
  "description": "Public event representation. It never contains createdBy, assignedPartners, revenueShares, privateNotes, communityInterestEstimate, or manager audit fields.",
  "required": [
    "id",
    "name",
    "type",
    "startDate",
    "endDate"
  ],
  "properties": {
    "id": {
      "type": "integer"
    },
    "name": {
      "type": "string"
    },
    "slug": {
      "type": [
        "string",
        "null"
      ]
    },
    "type": {
      "$ref": "#/components/schemas/EventType"
    },
    "description": {
      "type": [
        "string",
        "null"
      ]
    },
    "startDate": {
      "type": "string",
      "format": "date-time"
    },
    "endDate": {
      "type": "string",
      "format": "date-time"
    },
    "salesStartDate": {
      "type": [
        "string",
        "null"
      ],
      "format": "date-time"
    },
    "location": {
      "type": [
        "string",
        "null"
      ]
    },
    "capacity": {
      "type": "object",
      "additionalProperties": true
    },
    "batches": {
      "type": "array",
      "items": {}
    },
    "prices": {
      "type": "object",
      "additionalProperties": true
    },
    "discounts": {
      "type": "object",
      "additionalProperties": true
    },
    "fields": {
      "type": "object",
      "additionalProperties": true
    },
    "approvalRules": {
      "type": "array",
      "items": {}
    },
    "timers": {
      "type": "object",
      "additionalProperties": true
    },
    "speakers": {
      "type": "array",
      "items": {}
    },
    "sponsors": {
      "type": "array",
      "items": {}
    },
    "giveaways": {
      "type": "array",
      "items": {}
    },
    "imageUrl": {
      "type": [
        "string",
        "null"
      ]
    },
    "externalPageUrl": {
      "type": [
        "string",
        "null"
      ],
      "format": "uri"
    },
    "isActive": {
      "type": "boolean"
    },
    "isFeatured": {
      "type": "boolean"
    },
    "parentEventId": {
      "type": [
        "integer",
        "null"
      ]
    },
    "requiresParentTicket": {
      "type": "boolean"
    },
    "allowedPriceTiers": {
      "type": "array",
      "items": {
        "type": "string"
      }
    },
    "allowedTierUnlocks": {
      "type": "array",
      "items": {
        "type": "integer"
      }
    },
    "eventCategory": {
      "type": [
        "string",
        "null"
      ]
    },
    "eventTiming": {
      "type": [
        "string",
        "null"
      ]
    },
    "waitlistTimeLimit": {
      "type": [
        "integer",
        "null"
      ]
    },
    "enableBadges": {
      "type": "boolean"
    },
    "badgeTemplate": {
      "type": [
        "string",
        "null"
      ]
    },
    "enableAdditionalOptions": {
      "type": "boolean"
    },
    "enableGroupPurchase": {
      "type": "boolean"
    },
    "attendeeDirectoryEnabled": {
      "type": "boolean"
    },
    "communityInterestEnabled": {
      "type": "boolean"
    },
    "communityInterestCount": {
      "type": "integer",
      "minimum": 0,
      "description": "Present when Community Interest is enabled."
    },
    "timezone": {
      "type": [
        "string",
        "null"
      ]
    },
    "revision": {
      "type": "integer"
    },
    "createdAt": {
      "type": [
        "string",
        "null"
      ],
      "format": "date-time"
    },
    "updatedAt": {
      "type": [
        "string",
        "null"
      ],
      "format": "date-time"
    }
  },
  "additionalProperties": false
}
```

### PromotionalMaterial

```json
{
  "type": "object",
  "properties": {
    "id": {
      "type": "integer"
    },
    "eventId": {
      "type": "integer"
    },
    "title": {
      "type": "string"
    },
    "type": {
      "type": "string"
    },
    "description": {
      "type": [
        "string",
        "null"
      ]
    },
    "url": {
      "type": "string"
    },
    "displayOrder": {
      "type": "integer"
    }
  },
  "additionalProperties": true
}
```

### FomoResponse

```json
{
  "type": "object",
  "required": [
    "slug",
    "name",
    "capacity",
    "communityInterest",
    "timers",
    "now"
  ],
  "properties": {
    "slug": {
      "type": "string"
    },
    "name": {
      "type": "string"
    },
    "salesStartDate": {
      "type": [
        "string",
        "null"
      ],
      "format": "date-time"
    },
    "capacity": {
      "oneOf": [
        {
          "$ref": "#/components/schemas/CapacitySnapshot"
        },
        {
          "type": "null"
        }
      ]
    },
    "communityInterest": {
      "oneOf": [
        {
          "$ref": "#/components/schemas/CommunityInterest"
        },
        {
          "type": "null"
        }
      ]
    },
    "timers": {
      "type": "object",
      "additionalProperties": true
    },
    "now": {
      "type": "string",
      "format": "date-time"
    }
  },
  "additionalProperties": false
}
```

### CapacitySnapshot

```json
{
  "type": "object",
  "required": [
    "total",
    "sold",
    "remaining",
    "soldOut"
  ],
  "properties": {
    "total": {
      "type": "integer"
    },
    "sold": {
      "type": "integer"
    },
    "remaining": {
      "type": "integer"
    },
    "soldOut": {
      "type": "boolean"
    }
  },
  "additionalProperties": false
}
```

### CommunityInterest

```json
{
  "type": "object",
  "required": [
    "count",
    "label"
  ],
  "properties": {
    "count": {
      "type": "integer",
      "minimum": 0
    },
    "label": {
      "const": "people interested or attending"
    }
  },
  "additionalProperties": false
}
```

### PublicTierResponse

```json
{
  "type": "object",
  "required": [
    "slug",
    "name",
    "currency",
    "tiers"
  ],
  "properties": {
    "slug": {
      "type": "string"
    },
    "name": {
      "type": "string"
    },
    "currency": {
      "type": "string"
    },
    "tiers": {
      "type": "array",
      "items": {
        "$ref": "#/components/schemas/PublicTier"
      }
    }
  },
  "additionalProperties": false
}
```

### PublicTier

```json
{
  "type": "object",
  "properties": {
    "name": {
      "type": "string"
    },
    "price": {
      "type": "number"
    },
    "originalPrice": {
      "type": [
        "number",
        "null"
      ]
    },
    "description": {
      "type": [
        "string",
        "null"
      ]
    },
    "capacity": {
      "type": [
        "integer",
        "null"
      ]
    },
    "soldOut": {
      "type": "boolean"
    },
    "applyUrl": {
      "type": "string",
      "format": "uri"
    }
  },
  "additionalProperties": false
}
```

### SessionUser

```json
{
  "type": "object",
  "properties": {
    "id": {
      "type": "string",
      "format": "uuid"
    },
    "email": {
      "type": "string",
      "format": "email"
    },
    "username": {
      "type": [
        "string",
        "null"
      ]
    },
    "tier": {
      "type": [
        "string",
        "null"
      ]
    },
    "credits": {
      "type": [
        "integer",
        "null"
      ]
    },
    "roles": {
      "type": "array",
      "items": {
        "type": "string"
      }
    },
    "attendeeDirectoryOptIn": {
      "type": "boolean"
    }
  },
  "additionalProperties": true
}
```

### BooleanPreference

```json
{
  "type": "object",
  "required": [
    "enabled"
  ],
  "properties": {
    "enabled": {
      "type": "boolean"
    }
  },
  "additionalProperties": false
}
```

### Ticket

```json
{
  "type": "object",
  "properties": {
    "id": {
      "type": "integer"
    },
    "eventId": {
      "type": "integer"
    },
    "userId": {
      "type": "string",
      "format": "uuid"
    },
    "type": {
      "type": [
        "string",
        "null"
      ]
    },
    "status": {
      "type": "string",
      "enum": [
        "pending_app",
        "pending_pay",
        "paid",
        "checked_in",
        "cancelled"
      ]
    },
    "applicationData": {
      "type": "object",
      "additionalProperties": true
    },
    "gemsUsed": {
      "type": [
        "integer",
        "null"
      ]
    },
    "deadline": {
      "type": [
        "string",
        "null"
      ],
      "format": "date-time"
    }
  },
  "additionalProperties": true
}
```

### PublicDirectoryProfile

```json
{
  "type": "object",
  "required": [
    "username",
    "name",
    "photoUrl",
    "title",
    "company",
    "location",
    "bio",
    "profileUrl"
  ],
  "properties": {
    "username": {
      "type": "string"
    },
    "name": {
      "type": "string"
    },
    "photoUrl": {
      "type": [
        "string",
        "null"
      ],
      "format": "uri"
    },
    "title": {
      "type": [
        "string",
        "null"
      ]
    },
    "company": {
      "type": [
        "string",
        "null"
      ]
    },
    "location": {
      "type": [
        "string",
        "null"
      ]
    },
    "bio": {
      "type": [
        "string",
        "null"
      ]
    },
    "profileUrl": {
      "type": "string",
      "format": "uri"
    }
  },
  "additionalProperties": false
}
```

### AttendeeDirectoryResponse

```json
{
  "type": "object",
  "required": [
    "enabled",
    "viewerConfirmed",
    "canView",
    "attendees"
  ],
  "properties": {
    "enabled": {
      "type": "boolean"
    },
    "viewerConfirmed": {
      "type": "boolean"
    },
    "canView": {
      "type": "boolean"
    },
    "attendees": {
      "type": "array",
      "maxItems": 100,
      "items": {
        "$ref": "#/components/schemas/PublicDirectoryProfile"
      }
    }
  },
  "additionalProperties": false
}
```

### CommunityFeatureSettings

```json
{
  "type": "object",
  "required": [
    "attendeeDirectoryEnabled",
    "canManageDirectory",
    "confirmedCount",
    "visibleProfileCount",
    "communityInterestEnabled",
    "communityInterestEstimate",
    "communityInterestDisplayCount"
  ],
  "properties": {
    "attendeeDirectoryEnabled": {
      "type": "boolean"
    },
    "canManageDirectory": {
      "type": "boolean"
    },
    "confirmedCount": {
      "type": "integer",
      "minimum": 0
    },
    "visibleProfileCount": {
      "type": "integer",
      "minimum": 0
    },
    "communityInterestEnabled": {
      "type": "boolean"
    },
    "communityInterestEstimate": {
      "type": "integer",
      "minimum": 0,
      "maximum": 1000000
    },
    "communityInterestDisplayCount": {
      "type": "integer",
      "minimum": 0
    }
  },
  "additionalProperties": false
}
```

### Error

```json
{
  "type": "object",
  "required": [
    "error"
  ],
  "properties": {
    "error": {
      "type": "string"
    }
  },
  "additionalProperties": true
}
```
