pitch-connect.space / api/docs

API Reference

REST API · All responses are JSON · Auth via Bearer token

Pitch Connect — AI Agent & LLM Integration Guide

Tournaments support three accepted teams in one group with two advancing directly to a final. Intra-club drafts must be finalized before starting groups. A single round robin produces three group matches; no semifinal or third-place match is generated. Standings rank by points, goal difference, then goals scored, followed by head-to-head and fair play; exact remaining ties use participation ID for stable ordering. Stage transitions are performed in the browser, not through a bearer-token API endpoint.

Dedicated integration guide for AI Agents, autonomous coding assistants (Antigravity, Cursor, Claude, GPT, AutoGPT, LangChain), and third-party tools connecting to Pitch Connect.


  • Standard LLM Index: /llms.txt
  • Full LLM Context Specification: /llms-full.txt
  • OpenAPI 3.0 Spec (JSON): GET /api/openapi.json
  • OpenAPI 3.0 Spec (YAML): GET /api/openapi.yaml
  • Interactive Documentation: GET /api/docs/interactive
  • HTML API Guide: GET /api/docs
  • AI Agent Doc Page: GET /api/docs/ai

2. Authentication Model

Public tournament applications are an interactive browser workflow, not an AI tool/API workflow. Paid, capacity-limited intra-club applications use an organizer-configured spot hold (15 minutes by default) before displaying payment instructions; agents must not automate or bypass that hold. A hold created before registration closes remains valid only until its own expiration, while new holds are blocked after the deadline.

Organizing-club members and directly invited players use the same browser application. Paid applications require payment-confirmation evidence, and the legacy direct-registration endpoint redirects into this unified flow.

Organizer-configured Zelle and Venmo details may also appear in the browser workflow for inter-club team applications; those team applications do not use player-capacity holds.

Every API call to Pitch Connect requires a Bearer Token in the Authorization header:

Authorization: Bearer <your_api_key>

How an AI Agent Obtains a Token

  1. OAuth Connection Flow: Prompt the user to visit: GET https://pitch-connect.space/api/auth/connect?app_name=YourAgent&redirect_uri=https://your-agent.com/callback
  2. Callback Handling: Pitch Connect redirects the user back to https://your-agent.com/callback?api_key=<token>&resource_type=account.
  3. Store & Access: Store <token> securely and include it in subsequent HTTP requests.

sequenceDiagram
    autonumber
    participant Agent as AI Agent / LLM
    participant API as Pitch Connect API

    Agent->>API: GET /api/v1/resources (Bearer Token)
    API-->>Agent: Returns accessible clubs & tournaments

    Agent->>API: GET /api/v1/tournaments/:slug/matches
    API-->>Agent: Returns live scores, lineups & markers

    Agent->>API: POST /api/v1/tournaments/:slug/matches/:id/markers (Submit Goal/Card)
    API-->>Agent: Returns updated score & marker ID

    opt Revert / Correction
        Agent->>API: DELETE /api/v1/tournaments/:slug/matches/:id/markers/:marker_id
        API-->>Agent: Score auto-reverted, returns updated score
    end

4. Function Tool Schemas for LLM Function Calling

Real-time marker consumers

Connect to wss://pitch-connect.space/cable, send
Origin: https://pitch-connect.space, and negotiate the
actioncable-v1-json subprotocol. Subscribe with:

{
  "command": "subscribe",
  "identifier": "{\"channel\":\"GameLiveChannel\",\"game_id\":55}"
}

Both the initial subscribed message and every live_update contain the
current score/status, projected goals and cards arrays, and the complete
chronological markers array. Consumers should replace all three collections
on each payload and reconcile granular markers by marker id. Derive shots,
saves, substitutions, fouls, and detailed timelines from markers; use goals
and cards for rendering. Historical records explicitly remain legacy-backed
when markers are absent; do not infer authority from marker presence. Clean
marker-backed sessions create linked markers from web and API controls. Full
snapshots mean edits, resets, and deletions do not require a
separate compensating event.

Junior players in pickup-game markers

Pickup-game roster entries include both id and player_type. When submitting a marker for a saved junior member, send the junior's roster ID in primary_player_pc_id or secondary_player_pc_id and send the matching type:

{
  "id": "client-marker-uuid",
  "match_id": "301_0",
  "timestamp": "2026-07-27T18:30:00Z",
  "type": "Goal",
  "primary_player_pc_id": 17,
  "primary_player_type": "junior"
}

Use player_type: "user" for regular players. Types can be inferred from the game roster when omitted, but agents should always pass them because user and junior IDs come from separate numeric namespaces. Junior goals, cards, and contribution markers are attributed to their assigned team and included in the rendered match timeline and statistics.

If your AI Agent uses OpenAI, Anthropic, or Gemini function-calling / tools, here is the ready-to-use JSON tool definition array:

[
  {
    "name": "list_pitch_connect_resources",
    "description": "Discover all clubs and tournaments accessible by the current API token.",
    "parameters": { "type": "object", "properties": {} }
  },
  {
    "name": "list_public_tournaments",
    "description": "List all public tournaments on Pitch Connect with basic metadata (slug, name, format, status, dates, host_club, and public URL).",
    "parameters": {
      "type": "object",
      "properties": {},
      "required": []
    }
  },
  {
    "name": "get_tournament_matches",
    "description": "Retrieve all matches in a tournament with live score, lineups, and goal details.",
    "parameters": {
      "type": "object",
      "properties": {
        "tournament_slug": { "type": "string", "description": "The unique slug of the tournament" }
      },
      "required": ["tournament_slug"]
    }
  },
  {
    "name": "submit_match_event_marker",
    "description": "Submit a live marker event (Goal, YellowCard, RedCard, Substitution, Period) to a match.",
    "parameters": {
      "type": "object",
      "properties": {
        "tournament_slug": { "type": "string", "description": "Tournament slug" },
        "match_id": { "type": "integer", "description": "Match ID" },
        "type": { "type": "string", "enum": ["Start", "Goal", "YellowCard", "RedCard", "Substitution", "Break", "Resume", "PenaltyScored", "PenaltyMissed", "PenaltyShootout", "ResetMatch"] },
        "client_id": { "type": "string", "description": "Idempotent UUID" },
        "minute": { "type": "integer", "description": "Match minute" },
        "team_side": { "type": "string", "enum": ["home", "away"] },
        "primary_player_pc_id": { "type": "integer", "description": "Pitch Connect User ID for scorer/player" }
      },
      "required": ["tournament_slug", "match_id", "type", "client_id"]
    }
  },
  {
    "name": "delete_match_event_marker",
    "description": "Delete a marker by ID or client_id and automatically revert goal count and team scores.",
    "parameters": {
      "type": "object",
      "properties": {
        "tournament_slug": { "type": "string", "description": "Tournament slug" },
        "match_id": { "type": "integer", "description": "Match ID" },
        "id": { "type": "integer", "description": "Marker ID or client_id" }
      },
      "required": ["tournament_slug", "match_id", "id"]
    }
  }
]