openapi: 3.0.0
paths:
  /v1/health:
    get:
      description: >-
        Runs liveness and readiness checks for the API: PostgreSQL connectivity, Redis connectivity,
        process heap and RSS memory usage, and (in production) disk space. Returns an aggregated
        health report.
      operationId: check
      parameters: []
      responses:
        '200':
          description: >-
            All health indicators are up. Returns a Terminus health-check result with status "ok"
            and per-indicator details (e.g. db_master, redis, api_memory_heap, api_memory_rss,
            api_disk_space).
        '429': &ref_1
          description: >-
            Rate limit exceeded (60 requests/min per client IP by default; some endpoints override
            this). See the X-RateLimit-* and Retry-After headers.
          headers:
            Retry-After:
              description: Seconds to wait before retrying.
              schema:
                type: integer
            X-RateLimit-Limit:
              description: Request quota for the current window.
              schema:
                type: integer
            X-RateLimit-Remaining:
              description: Requests remaining in the current window.
              schema:
                type: integer
            X-RateLimit-Reset:
              description: Seconds until the window resets.
              schema:
                type: integer
          content: &ref_0
            application/json:
              schema:
                $ref: '#/components/schemas/ApiError'
        '503':
          description: >-
            One or more health indicators are down. Returns a Terminus health-check result with
            status "error" and the failing indicator details.
      summary: Service health check
      tags:
        - Health
  /v1/acars/decode:
    post:
      description: >-
        Decodes the raw text of an ACARS message for the given ACARS label and returns the decoded
        structured payload. The shape of the response depends on the message label and content.
      operationId: decode
      parameters: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/DecodeAcarsDto'
      responses:
        '201':
          description: The decoded ACARS message payload. Structure varies by label and message content.
        '401': &ref_2
          description: Authentication required or the credentials are invalid.
          content: *ref_0
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Decode an ACARS message
      tags:
        - ACARS
  /v1/airlines:
    get:
      description: Returns a paginated list of airlines. Results are cached for 6 hours.
      operationId: findAll
      parameters:
        - name: sort
          required: false
          in: query
          description: Field to sort by. Prefix with `-` for descending order. Defaults to `icao`.
          schema:
            example: icao
        - name: limit
          required: false
          in: query
          description: Maximum number of airlines per page. Defaults to 100.
          schema:
            example: 100
            type: number
        - name: page
          required: false
          in: query
          description: Page number for pagination (1-based). Defaults to 1.
          schema:
            example: 1
            type: number
      responses:
        '200':
          description: A paginated array of airlines.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airline'
        '401': *ref_2
        '429': *ref_1
      security: &ref_3
        - api-key: []
        - bearer: []
      summary: List airlines
      tags: &ref_4
        - Airlines
  /v1/airlines/{id}:
    get:
      description: Returns a single airline by its database ID. Result is cached for 6 hours.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Database ID of the airline.
          schema:
            example: '42'
            type: string
      responses:
        '200':
          description: The matching airline, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airline'
        '401': *ref_2
        '429': *ref_1
      security: *ref_3
      summary: Get airline by ID
      tags: *ref_4
  /v1/airlines/icao/{icao}:
    get:
      description: >-
        Returns a single airline matching the given 3-letter ICAO airline code. Result is cached for
        6 hours.
      operationId: findOneByIcao
      parameters:
        - name: icao
          required: true
          in: path
          description: ICAO airline code (3 letters).
          schema:
            example: UAL
            type: string
      responses:
        '200':
          description: The matching airline, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airline'
        '401': *ref_2
        '429': *ref_1
      security: *ref_3
      summary: Get airline by ICAO code
      tags: *ref_4
  /v1/airlines/iata/{iata}:
    get:
      description: >-
        Returns all airlines matching the given 2-character IATA airline code. Results are cached
        for 6 hours.
      operationId: findAllByIata
      parameters:
        - name: iata
          required: true
          in: path
          description: IATA airline code (2 characters).
          schema:
            example: UA
            type: string
      responses:
        '200':
          description: An array of airlines matching the IATA code.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airline'
        '401': *ref_2
        '429': *ref_1
      security: *ref_3
      summary: List airlines by IATA code
      tags: *ref_4
  /v1/airframes/routes:
    get:
      description: >-
        Returns the great-circle path between two airports (resolved by ICAO, ident or IATA), as an
        interpolated list of points plus distance and initial bearing. Useful for drawing a
        planned/idealized route.
      operationId: greatCircleRoute
      parameters:
        - name: from
          required: true
          in: query
          description: Departure airport (ICAO, ident or IATA).
          schema:
            example: KSFO
            type: string
        - name: to
          required: true
          in: query
          description: Destination airport (ICAO, ident or IATA).
          schema:
            example: KJFK
            type: string
        - name: points
          required: false
          in: query
          description: >-
            Number of interpolation segments (1–1000, default 64). The response contains points + 1
            entries.
          schema:
            example: 64
            type: string
      responses:
        '200':
          description: ''
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/GreatCircleRouteResponseDto'
        '400':
          description: Missing `from`/`to`.
        '401': *ref_2
        '404':
          description: Unknown airport.
        '429': *ref_1
      security: &ref_5
        - api-key: []
        - bearer: []
      summary: Great-circle route between two airports
      tags: &ref_6
        - Routes
  /v1/airframes/flights/{id}/route:
    get:
      description: >-
        Returns a flight's route. When ADS-B positions exist, this is the actual flown track
        (`source: "flown"`); otherwise it falls back to a synthesized great-circle line between the
        departure and destination airports (`source: "great_circle"`). If neither is available,
        `source: "none"` with an empty `points` array.
      operationId: flightRoute
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 5544014689
            type: string
        - name: hours
          required: false
          in: query
          description: Window (hours) for the flown track (default 48).
          schema:
            example: 48
            type: string
        - name: limit
          required: false
          in: query
          description: Max flown points to return (default 2000).
          schema:
            example: 2000
            type: string
        - name: points
          required: false
          in: query
          description: Segments for the great-circle fallback (1–1000, default 64).
          schema:
            example: 64
            type: string
      responses:
        '200':
          description: ''
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FlightRouteResponseDto'
        '401': *ref_2
        '404':
          description: Flight not found.
        '429': *ref_1
      security: *ref_5
      summary: Route for a flight
      tags: *ref_6
  /v1/flights:
    get:
      description: >-
        Returns the most recent flights from the database. The result count is clamped between 1 and
        500 (defaults to 100).
      operationId: findAll
      parameters:
        - name: limit
          required: false
          in: query
          description: Maximum number of flights to return (clamped to 1–500).
          schema:
            example: 100
            type: string
      responses:
        '200':
          description: An array of the most recent flights.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '429': *ref_1
      summary: List recent flights
      tags: &ref_7
        - Flights
  /v1/flights/active:
    get:
      description: >-
        Returns currently active flights, served from a short-lived Redis cache when available.
        Requires authentication via JWT or API key. Arbitrary query parameters are passed through as
        filters.
      operationId: findActive
      parameters:
        - name: dep_airport
          required: false
          in: query
          description: Filter to flights departing from this airport ICAO code.
          schema:
            example: KLAX
            type: string
        - name: arr_airport
          required: false
          in: query
          description: Filter to flights arriving at this airport ICAO code.
          schema:
            example: KSFO
            type: string
      responses:
        '200':
          description: An array of active flights.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List active flights
      tags: *ref_7
  /v1/flights/active/{id}:
    get:
      description: >-
        Returns a single active flight by its numeric id, served from a short-lived Redis cache when
        available.
      operationId: findOneActive
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 123456
            type: string
      responses:
        '200':
          description: The matching active flight (or null if not found).
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Flight'
        '429': *ref_1
      summary: Get an active flight by id
      tags: *ref_7
  /v1/flights/live:
    get:
      description: >-
        Returns all live aircraft flights directly from the Redis entity cache with no database
        query — suitable for real-time map UIs. Requires authentication via JWT or API key.
      operationId: findLive
      parameters:
        - name: withPosition
          required: false
          in: query
          description: Set to "true" to only return flights that currently have a position.
          schema:
            example: 'true'
            type: string
        - name: limit
          required: false
          in: query
          description: Maximum number of flights to return (default 5000, clamped to 1–10000).
          schema:
            example: 5000
            type: string
      responses:
        '200':
          description: An array of live flights from the entity cache (not a persisted entity shape).
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/LiveFlightDto'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List live flights from cache
      tags: *ref_7
  /v1/flights/live/{cacheId}:
    get:
      description: >-
        Returns a single live flight, including its full position trail, from the Redis entity
        cache. Returns null if the flight is not in the cache. Requires authentication via JWT or
        API key.
      operationId: findOneLive
      parameters:
        - name: cacheId
          required: true
          in: path
          description: Entity cache id of the live flight.
          schema:
            example: A1B2C3
            type: string
      responses:
        '200':
          description: >-
            The live flight with an optional trail array, or null if not cached (not a persisted
            entity shape).
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/LiveFlightDto'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get a live flight with trail
      tags: *ref_7
  /v1/flights/{id}/messages:
    get:
      description: >-
        Returns paginated messages for a flight. Page size is capped at 100, and the lookup can be
        bounded to a recent window to prune partitions and speed up the query.
      operationId: findMessages
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 123456
            type: string
        - name: page
          required: false
          in: query
          description: Page number, 1-based (default 1).
          schema:
            example: 1
            type: string
        - name: limit
          required: false
          in: query
          description: Messages per page (default 100, capped at 100).
          schema:
            example: 100
            type: string
        - name: sinceHours
          required: false
          in: query
          description: Restrict to messages within the last N hours to prune partitions and speed up the query.
          schema:
            example: 24
            type: string
      responses:
        '200':
          description: A paginated set of messages for the flight.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Message'
        '429': *ref_1
      summary: List messages for a flight
      tags: *ref_7
  /v1/flights/{id}/events:
    get:
      description: >-
        Returns flight events, capped and time-bounded, served from a short-lived Redis cache when
        available. Loaded independently by the flight detail UI.
      operationId: findEvents
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 123456
            type: string
      responses:
        '200':
          description: An array of flight events.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/FlightEvent'
        '429': *ref_1
      summary: List events for a flight
      tags: *ref_7
  /v1/flights/{id}/positions:
    get:
      description: >-
        Returns recent flight positions for the map, capped and time-bounded, served from a
        short-lived Redis cache when available. Degrades to an empty array instead of failing if the
        positions query errors (e.g. a statement timeout).
      operationId: findPositions
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 123456
            type: string
        - name: hours
          required: false
          in: query
          description: Restrict positions to the last N hours.
          schema:
            example: 6
            type: string
      responses:
        '200':
          description: An array of recent flight positions (empty if the query degrades).
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/FlightPosition'
        '429': *ref_1
      summary: List positions for a flight
      tags: *ref_7
  /v1/flights/{id}:
    get:
      description: >-
        Returns flight detail including airframe, airline, events, and recent messages (bounded to a
        recent window). Positions are not joined by default — fetch them from /flights/:id/positions
        — unless include=positions is passed. Served from a Redis cache with a short TTL for
        in-flight flights and a longer TTL for completed ones.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric flight id.
          schema:
            example: 123456
            type: string
        - name: include
          required: false
          in: query
          description: >-
            Comma-separated list of extra relations to load inline. Pass "positions" to also load
            positions inline (legacy globe/map callers).
          schema:
            example: positions
            type: string
      responses:
        '200':
          description: The flight detail with related airframe, airline, and events.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Flight'
        '429': *ref_1
      summary: Get flight detail by id
      tags: *ref_7
  /v1/flights/bbox/{xmin},{ymin},{xmax},{ymax}:
    get:
      description: >-
        Returns flights whose position falls within the given geographic bounding box. Returns an
        empty array if any bound is infinite. Requires authentication via JWT or API key.
      operationId: findByBoundingBox
      parameters:
        - name: xmin
          required: true
          in: path
          description: Minimum longitude of the bounding box.
          schema:
            example: '-122.5'
            type: string
        - name: ymin
          required: true
          in: path
          description: Minimum latitude of the bounding box.
          schema:
            example: '37.2'
            type: string
        - name: xmax
          required: true
          in: path
          description: Maximum longitude of the bounding box.
          schema:
            example: '-121.8'
            type: string
        - name: ymax
          required: true
          in: path
          description: Maximum latitude of the bounding box.
          schema:
            example: '37.9'
            type: string
      responses:
        '200':
          description: An array of flights within the bounding box.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List flights within a bounding box
      tags: *ref_7
  /v1/airframes:
    get:
      description: >-
        Returns a paginated list of airframes (aircraft). Supports optional filtering by tail number
        and airline. Results are cached for 1 hour.
      operationId: findAll
      parameters:
        - name: airlineId
          required: false
          in: query
          description: Filter airframes by the owning airline ID.
          schema:
            example: '42'
        - name: tail
          required: false
          in: query
          description: Filter airframes by tail (registration) number (prefix match).
          schema:
            example: N12345
        - name: sort
          required: false
          in: query
          description: >-
            Field to sort by. Prefix with `-` for descending order (e.g. `-icao`). Defaults to
            `icao`.
          schema:
            example: icao
        - name: limit
          required: false
          in: query
          description: Maximum number of airframes per page. Defaults to 100.
          schema:
            example: 100
            type: number
        - name: page
          required: false
          in: query
          description: Page number for pagination (1-based). Defaults to 1.
          schema:
            example: 1
            type: number
      responses:
        '200':
          description: A paginated array of matching airframes.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airframe'
        '401': *ref_2
        '429': *ref_1
      security: &ref_8
        - api-key: []
        - bearer: []
      summary: List airframes
      tags: &ref_9
        - Airframes
  /v1/airframes/{id}:
    get:
      description: Returns a single airframe by its numeric database ID. Result is cached for 1 hour.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric database ID of the airframe.
          schema:
            example: '12345'
            type: string
      responses:
        '200':
          description: The matching airframe, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airframe'
        '401': *ref_2
        '429': *ref_1
      security: *ref_8
      summary: Get airframe by ID
      tags: *ref_9
  /v1/airframes/tail/{tail}:
    get:
      description: >-
        Returns a single airframe matching the given tail (registration) number. Result is cached
        for 1 hour.
      operationId: findOneByTail
      parameters:
        - name: tail
          required: true
          in: path
          description: Tail (registration) number of the airframe.
          schema:
            example: N12345
            type: string
      responses:
        '200':
          description: The matching airframe, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airframe'
        '401': *ref_2
        '429': *ref_1
      security: *ref_8
      summary: Get airframe by tail number
      tags: *ref_9
  /v1/airframes/icao/{icao}:
    get:
      description: >-
        Returns a single airframe matching the given ICAO 24-bit address / code. Result is cached
        for 1 hour.
      operationId: findOneByIcao
      parameters:
        - name: icao
          required: true
          in: path
          description: ICAO code of the airframe.
          schema:
            example: A12B34
            type: string
      responses:
        '200':
          description: The matching airframe, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airframe'
        '401': *ref_2
        '429': *ref_1
      security: *ref_8
      summary: Get airframe by ICAO code
      tags: *ref_9
  /v1/airframes/iata/{iata}:
    get:
      description: Returns a single airframe matching the given IATA code. Result is cached for 1 hour.
      operationId: findOneByIata
      parameters:
        - name: iata
          required: true
          in: path
          description: IATA code of the airframe.
          schema:
            example: '320'
            type: string
      responses:
        '200':
          description: The matching airframe, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airframe'
        '401': *ref_2
        '429': *ref_1
      security: *ref_8
      summary: Get airframe by IATA code
      tags: *ref_9
  /v1/airports:
    get:
      description: Returns a paginated list of airports, ICAO-ordered. Results are cached for 6 hours.
      operationId: findAll
      parameters:
        - name: limit
          required: false
          in: query
          description: Maximum number of airports per page. Defaults to 100.
          schema:
            example: 100
            type: number
        - name: page
          required: false
          in: query
          description: Page number for pagination (1-based). Defaults to 1.
          schema:
            example: 1
            type: number
      responses:
        '200':
          description: A paginated array of airports (ICAO-ordered).
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: &ref_10
        - &ref_12
          api-key: []
        - &ref_13
          bearer: []
      summary: List airports
      tags: &ref_11
        - Airports
  /v1/airports/{id}:
    get:
      description: >-
        Returns a single airport by its UUID. The ID must be a valid UUID or a 400 is returned.
        Result is cached for 6 hours.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: UUID of the airport.
          schema:
            example: 6c2e9f1a-1b2c-4d3e-8f9a-0b1c2d3e4f5a
            type: string
      responses:
        '200':
          description: The matching airport, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airport'
        '400':
          description: The provided ID is not a valid UUID.
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: Get airport by ID
      tags: *ref_11
  /v1/airports/icao/{icao}:
    get:
      description: >-
        Returns a single airport matching the given 4-letter ICAO airport code. Result is cached for
        6 hours.
      operationId: findOneByIcao
      parameters:
        - name: icao
          required: true
          in: path
          description: ICAO airport code (4 letters).
          schema:
            example: KSFO
            type: string
      responses:
        '200':
          description: The matching airport, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: Get airport by ICAO code
      tags: *ref_11
  /v1/airports/iata/{iata}:
    get:
      description: >-
        Returns a single airport matching the given 3-letter IATA airport code. Result is cached for
        6 hours.
      operationId: findOneByIata
      parameters:
        - name: iata
          required: true
          in: path
          description: IATA airport code (3 letters).
          schema:
            example: SFO
            type: string
      responses:
        '200':
          description: The matching airport, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: Get airport by IATA code
      tags: *ref_11
  /v1/airports/ident/{ident}:
    get:
      description: >-
        Returns a single airport matching the given OurAirports ident code. Result is cached for 6
        hours.
      operationId: findOneByIdent
      parameters:
        - name: ident
          required: true
          in: path
          description: Airport ident code (OurAirports identifier).
          schema:
            example: KSFO
            type: string
      responses:
        '200':
          description: The matching airport, or empty if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: Get airport by ident
      tags: *ref_11
  /v1/airports/type/{type}:
    get:
      description: Returns all airports matching the given airport type. Results are cached for 6 hours.
      operationId: findByType
      parameters:
        - name: type
          required: true
          in: path
          description: Airport type to filter by.
          schema:
            example: large_airport
            type: string
      responses:
        '200':
          description: An array of airports of the given type.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: List airports by type
      tags: *ref_11
  /v1/airports/bbox/{xmin},{ymin},{xmax},{ymax}:
    get:
      description: >-
        Returns all airports located within the geographic bounding box defined by the min/max
        longitude (x) and latitude (y) coordinates. Returns an empty array if any bound is infinite.
        Results are cached for 6 hours.
      operationId: findByBoundingBox
      parameters:
        - name: xmin
          required: true
          in: path
          description: Minimum longitude (west bound) of the bounding box.
          schema:
            example: '-123.0'
            type: string
        - name: ymin
          required: true
          in: path
          description: Minimum latitude (south bound) of the bounding box.
          schema:
            example: '37.0'
            type: string
        - name: xmax
          required: true
          in: path
          description: Maximum longitude (east bound) of the bounding box.
          schema:
            example: '-122.0'
            type: string
        - name: ymax
          required: true
          in: path
          description: Maximum latitude (north bound) of the bounding box.
          schema:
            example: '38.0'
            type: string
      responses:
        '200':
          description: An array of airports within the bounding box.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Airport'
        '401': *ref_2
        '429': *ref_1
      security: *ref_10
      summary: List airports within a bounding box
      tags: *ref_11
  /v1/airports/{icao}/flights:
    get:
      description: >-
        Returns the flights associated with the given airport ICAO code. Requires authentication via
        JWT or API key. This endpoint is not cached because flight data is dynamic.
      operationId: getFlightsByAirport
      parameters:
        - name: icao
          required: true
          in: path
          description: ICAO airport code (4 letters).
          schema:
            example: KSFO
            type: string
      responses:
        '200':
          description: An array of flights for the airport.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - *ref_12
        - *ref_13
        - api-key: []
        - bearer: []
      summary: List flights for an airport
      tags: *ref_11
  /v1/hfdl/ground-stations:
    get:
      description: >-
        Returns the fixed set of HFDL (High Frequency Data Link) ground stations, each enriched with
        its currently active frequencies and last-updated timestamp pulled from the cache. The
        response is a JSON-encoded string with a top-level "ground_stations" array.
      operationId: groundStations
      parameters: []
      responses:
        '200':
          description: >-
            JSON-encoded string containing a "ground_stations" array, each entry with id, name,
            active frequencies, and last_updated.
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List HFDL ground stations with active frequencies
      tags:
        - HFDL
  /v1/marine/voyages:
    get:
      description: >-
        Returns the most recent marine (AIS) vessel voyages, ordered by recency. Use the limit query
        parameter to control how many are returned.
      operationId: findAll
      parameters:
        - name: limit
          required: false
          in: query
          description: Maximum number of voyages to return. Clamped between 1 and 500; defaults to 100.
          schema:
            example: 100
            type: string
      responses:
        '200':
          description: A list of marine voyages.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/MarineVoyage'
        '401': *ref_2
        '429': *ref_1
      security: &ref_17
        - &ref_14
          api-key: []
        - &ref_15
          bearer: []
      summary: List marine voyages
      tags: &ref_16
        - Marine
  /v1/marine/voyages/active:
    get:
      description: >-
        Returns marine voyages that are currently active (recently heard vessels). Results are
        served from cache when available. Requires authentication.
      operationId: findActive
      parameters: []
      responses:
        '200':
          description: A list of currently active marine voyages.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/MarineVoyage'
        '401': *ref_2
        '429': *ref_1
      security:
        - *ref_14
        - *ref_15
        - api-key: []
        - bearer: []
      summary: List active marine voyages
      tags: *ref_16
  /v1/marine/voyages/{id}:
    get:
      description: Returns a single marine voyage by its unique identifier.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the marine voyage.
          schema:
            example: '67890'
            type: string
      responses:
        '200':
          description: The requested marine voyage.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MarineVoyage'
        '401': *ref_2
        '429': *ref_1
      security: *ref_17
      summary: Get a marine voyage by ID
      tags: *ref_16
  /v1/marine/voyages/{id}/positions:
    get:
      description: >-
        Returns the position reports recorded during a marine voyage, ordered chronologically
        (oldest first). Use the limit query parameter to control how many are returned.
      operationId: findPositions
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the marine voyage.
          schema:
            example: '67890'
            type: string
        - name: limit
          required: false
          in: query
          description: >-
            Maximum number of position reports to return. Clamped between 1 and 5000; defaults to
            2000.
          schema:
            example: 2000
            type: string
      responses:
        '200':
          description: A list of position reports for the voyage.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/MarineVoyagePosition'
        '401': *ref_2
        '429': *ref_1
      security: *ref_17
      summary: Get position reports for a marine voyage
      tags: *ref_16
  /v1/marine/voyages/{id}/messages:
    get:
      description: >-
        Returns the AIS messages received during a marine voyage, most recent first. Use the limit
        query parameter to control how many are returned.
      operationId: findMessages
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the marine voyage.
          schema:
            example: '67890'
            type: string
        - name: limit
          required: false
          in: query
          description: Maximum number of messages to return. Clamped between 1 and 500; defaults to 200.
          schema:
            example: 200
            type: string
      responses:
        '200':
          description: A list of AIS messages for the voyage.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/MarineMessage'
        '401': *ref_2
        '429': *ref_1
      security: *ref_17
      summary: Get AIS messages for a marine voyage
      tags: *ref_16
  /v1/marine/voyages/bbox/{xmin},{ymin},{xmax},{ymax}:
    get:
      description: >-
        Returns marine voyages whose last reported position falls within the geographic bounding box
        defined by the minimum and maximum longitude (x) and latitude (y). Returns an empty array if
        any bound is infinite. Requires authentication.
      operationId: findByBoundingBox
      parameters:
        - name: xmin
          required: true
          in: path
          description: Minimum longitude (western bound) in decimal degrees.
          schema:
            example: '-10.5'
            type: string
        - name: ymin
          required: true
          in: path
          description: Minimum latitude (southern bound) in decimal degrees.
          schema:
            example: '40.0'
            type: string
        - name: xmax
          required: true
          in: path
          description: Maximum longitude (eastern bound) in decimal degrees.
          schema:
            example: '10.5'
            type: string
        - name: ymax
          required: true
          in: path
          description: Maximum latitude (northern bound) in decimal degrees.
          schema:
            example: '55.0'
            type: string
      responses:
        '200':
          description: A list of marine voyages within the bounding box.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/MarineVoyage'
        '401': *ref_2
        '429': *ref_1
      security:
        - *ref_14
        - *ref_15
        - api-key: []
        - bearer: []
      summary: List marine voyages within a bounding box
      tags: *ref_16
  /v1/marine/vessels/{mmsi}:
    get:
      description: >-
        Returns a single marine vessel identified by its Maritime Mobile Service Identity (MMSI)
        number.
      operationId: findByMmsi
      parameters:
        - name: mmsi
          required: true
          in: path
          description: Maritime Mobile Service Identity (MMSI) number of the vessel.
          schema:
            example: '366998410'
            type: string
      responses:
        '200':
          description: The requested marine vessel.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MarineVessel'
        '401': *ref_2
        '404':
          description: No marine vessel found for the given MMSI.
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get a marine vessel by MMSI
      tags:
        - Marine
  /v1/messages:
    get:
      description: >-
        Returns a paginated list of decoded aviation messages (ACARS, VDL, HFDL, etc.) matching the
        supplied query parameters. Authentication is optional: providing a valid JWT or API key
        honors authenticated rate limits, but anonymous requests are also permitted. This endpoint
        is not cached due to the large number of possible query-parameter combinations.
      operationId: findAll
      parameters:
        - name: until
          required: false
          in: query
          description: ISO-8601 upper time bound (messages created at or before).
          schema:
            example: '2026-06-08T00:00:00Z'
            type: string
        - name: since
          required: false
          in: query
          description: ISO-8601 lower time bound (alias for created_at_after). Defaults to 24h ago.
          schema:
            example: '2026-06-01T00:00:00Z'
            type: string
        - name: text
          required: false
          in: query
          description: Substring to match case-insensitively (ILIKE) within the message text.
          schema:
            example: TURBULENCE
            type: string
        - name: icao
          required: false
          in: query
          description: ICAO hex code; matched case-insensitively (ILIKE) on from_hex.
          schema:
            example: a1b2c3
            type: string
        - name: exclude_errors
          required: false
          in: query
          description: Comma-separated list of error counts to exclude.
          schema:
            example: 1,2,3
            type: string
        - name: exclude_labels
          required: false
          in: query
          description: Comma-separated list of message labels to exclude.
          schema:
            example: Q0,SA
            type: string
        - name: labels
          required: false
          in: query
          description: Comma-separated list of message labels to include.
          schema:
            example: H1,5Z
            type: string
        - name: station_ids
          required: false
          in: query
          description: Comma-separated list of station ids to filter by.
          schema:
            example: 11,22,33
            type: string
        - name: flight_id
          required: false
          in: query
          description: Restrict results to a single flight id.
          schema:
            example: 123456
            type: number
        - name: airframe_ids
          required: false
          in: query
          description: Comma-separated list of airframe ids to filter by.
          schema:
            example: 101,202,303
            type: string
        - name: timeframe
          required: false
          in: query
          description: Relative time window for the query. Overrides created_at_after when supplied.
          schema:
            enum:
              - last-hour
              - last-6-hours
              - last-12-hours
              - last-day
              - last-3-days
              - last-week
              - last-month
              - last-3-months
            type: string
        - name: created_at_after
          required: false
          in: query
          description: >-
            ISO-8601 date/time lower bound; only messages created at or after this instant are
            returned. Defaults to now minus one day. Overridden by timeframe when both are supplied.
          schema:
            example: '2026-06-01T00:00:00Z'
            type: string
        - name: before_id
          required: false
          in: query
          description: >-
            Cursor for keyset pagination: only return messages with id < before_id. Takes precedence
            over offset.
          schema:
            example: 123456
            type: number
        - name: offset
          required: false
          in: query
          description: >-
            Number of messages to skip for pagination (default 0, max 500000). Ignored when
            before_id is supplied.
          schema:
            example: 0
            type: number
        - name: limit
          required: false
          in: query
          description: Maximum number of messages to return (default 100, max 100).
          schema:
            example: 100
            type: number
      responses:
        '200':
          description: Array of messages matching the query.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Message'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List messages
      tags: &ref_18
        - Messages
  /v1/messages/{id}:
    get:
      description: >-
        Returns a single message identified by its numeric primary key. Results are cached for 24
        hours because messages are immutable once stored.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric primary key (id) of the message.
          schema:
            example: '123456'
            type: string
      responses:
        '200':
          description: The message with the given ID.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Message'
        '429': *ref_1
      summary: Get a message by ID
      tags: *ref_18
  /v1/messages/ar_uuid/{id}:
    get:
      description: >-
        Returns a single message identified by its Airframes UUID (ar_uuid). Results are cached for
        24 hours because messages are immutable once stored.
      operationId: findOneByArUUID
      parameters:
        - name: id
          required: true
          in: path
          description: Airframes UUID (ar_uuid) of the message.
          schema:
            example: 550e8400-e29b-41d4-a716-446655440000
            type: string
      responses:
        '200':
          description: The message with the given Airframes UUID.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Message'
        '429': *ref_1
      summary: Get a message by Airframes UUID (ar_uuid)
      tags: *ref_18
  /v1/sonde/flights:
    get:
      description: >-
        Returns the most recent weather balloon (radiosonde) flights, ordered by recency. Use the
        limit query parameter to control how many are returned.
      operationId: findAll
      parameters:
        - name: limit
          required: false
          in: query
          description: Maximum number of flights to return. Clamped between 1 and 500; defaults to 100.
          schema:
            example: 100
            type: string
      responses:
        '200':
          description: A list of sonde flights.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeFlight'
        '401': *ref_2
        '429': *ref_1
      security: &ref_22
        - &ref_19
          api-key: []
        - &ref_20
          bearer: []
      summary: List sonde flights
      tags: &ref_21
        - Sonde
  /v1/sonde/flights/active:
    get:
      description: >-
        Returns weather balloon flights that are currently active (recently heard radiosondes).
        Results are served from cache when available. Requires authentication.
      operationId: findActive
      parameters: []
      responses:
        '200':
          description: A list of currently active sonde flights.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeFlight'
        '401': *ref_2
        '429': *ref_1
      security:
        - *ref_19
        - *ref_20
        - api-key: []
        - bearer: []
      summary: List active sonde flights
      tags: *ref_21
  /v1/sonde/flights/{id}:
    get:
      description: Returns a single weather balloon flight by its unique identifier.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the sonde flight.
          schema:
            example: '8842'
            type: string
      responses:
        '200':
          description: The requested sonde flight.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SondeFlight'
        '401': *ref_2
        '429': *ref_1
      security: *ref_22
      summary: Get a sonde flight by ID
      tags: *ref_21
  /v1/sonde/flights/{id}/positions:
    get:
      description: >-
        Returns the recorded position reports (track) for a single weather balloon flight, in
        chronological order (oldest first).
      operationId: findPositions
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the sonde flight.
          schema:
            example: '8842'
            type: string
        - name: limit
          required: false
          in: query
          description: >-
            Maximum number of position reports to return. Clamped between 1 and 5000; defaults to
            2000.
          schema:
            example: 2000
            type: string
      responses:
        '200':
          description: A chronological list of position reports for the flight.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeFlightPosition'
        '401': *ref_2
        '429': *ref_1
      security: *ref_22
      summary: List position reports for a sonde flight
      tags: *ref_21
  /v1/sonde/flights/{id}/messages:
    get:
      description: >-
        Returns the telemetry messages received during a single weather balloon flight, most recent
        first.
      operationId: findMessages
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the sonde flight.
          schema:
            example: '8842'
            type: string
        - name: limit
          required: false
          in: query
          description: Maximum number of messages to return. Clamped between 1 and 500; defaults to 200.
          schema:
            example: 200
            type: string
      responses:
        '200':
          description: A list of telemetry messages for the flight, newest first.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeMessage'
        '401': *ref_2
        '429': *ref_1
      security: *ref_22
      summary: List telemetry messages for a sonde flight
      tags: *ref_21
  /v1/sonde/flights/bbox/{xmin},{ymin},{xmax},{ymax}:
    get:
      description: >-
        Returns weather balloon flights whose last reported position falls within the geographic
        bounding box defined by the minimum and maximum longitude (x) and latitude (y). Returns an
        empty array if any bound is infinite. Requires authentication.
      operationId: findByBoundingBox
      parameters:
        - name: xmin
          required: true
          in: path
          description: Minimum longitude (western bound) in decimal degrees.
          schema:
            example: '-10.5'
            type: string
        - name: ymin
          required: true
          in: path
          description: Minimum latitude (southern bound) in decimal degrees.
          schema:
            example: '40.0'
            type: string
        - name: xmax
          required: true
          in: path
          description: Maximum longitude (eastern bound) in decimal degrees.
          schema:
            example: '10.5'
            type: string
        - name: ymax
          required: true
          in: path
          description: Maximum latitude (northern bound) in decimal degrees.
          schema:
            example: '55.0'
            type: string
      responses:
        '200':
          description: A list of sonde flights within the bounding box.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeFlight'
        '401': *ref_2
        '429': *ref_1
      security:
        - *ref_19
        - *ref_20
        - api-key: []
        - bearer: []
      summary: List sonde flights within a bounding box
      tags: *ref_21
  /v1/sonde/sites:
    get:
      description: >-
        Returns radiosonde (weather balloon) launch sites. Use the limit query parameter to control
        how many are returned.
      operationId: findAll
      parameters:
        - name: limit
          required: false
          in: query
          description: Maximum number of launch sites to return. Clamped between 1 and 500; defaults to 200.
          schema:
            example: 200
            type: string
      responses:
        '200':
          description: A list of sonde launch sites.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/SondeSite'
        '401': *ref_2
        '429': *ref_1
      security: &ref_23
        - api-key: []
        - bearer: []
      summary: List sonde launch sites
      tags: &ref_24
        - Sonde
  /v1/sonde/sites/{id}:
    get:
      description: Returns a single radiosonde launch site by its unique identifier.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Unique identifier of the sonde launch site.
          schema:
            example: '155'
            type: string
      responses:
        '200':
          description: The requested sonde launch site.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SondeSite'
        '401': *ref_2
        '404':
          description: No sonde launch site exists with the given ID.
        '429': *ref_1
      security: *ref_23
      summary: Get a sonde launch site by ID
      tags: *ref_24
  /v1/sonde/sondes/{serial}:
    get:
      description: Returns a single radiosonde (weather balloon transmitter) by its serial number.
      operationId: findBySerial
      parameters:
        - name: serial
          required: true
          in: path
          description: Serial number of the radiosonde unit.
          schema:
            example: S4830127
            type: string
      responses:
        '200':
          description: The requested radiosonde.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Sonde'
        '401': *ref_2
        '404':
          description: No radiosonde exists with the given serial number.
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get a radiosonde by serial number
      tags:
        - Sonde
  /v1/stations:
    get:
      description: >-
        Returns all visible stations as a JSON array. Responses are served from a Redis cache
        (pre-gzipped when the client sends Accept-Encoding: gzip) and refreshed roughly every 10
        seconds; sensitive fields are stripped and IPs masked before serialization. Falls back to a
        live database query on a cache miss. Cached for 10 seconds (public).
      operationId: findAll
      parameters: []
      responses:
        '200':
          description: Array of stations.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Station'
        '401': *ref_2
        '429': *ref_1
      security: &ref_25
        - api-key: []
        - bearer: []
      summary: List all stations
      tags: &ref_26
        - Stations
  /v1/stations/{id}:
    get:
      description: >-
        Returns a single station by its numeric ID, enriched with its GeoJSON coverage polygon and
        range-ring coverage circles (50/100/150/200nm) when available. Returns null if no station
        matches the ID.
      operationId: findOneById
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric station ID (positive integer).
          schema:
            example: 1234
            type: string
      responses:
        '200':
          description: The matching station, or null if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Station'
        '400':
          description: The station ID is malformed (must be a positive integer).
        '401': *ref_2
        '429': *ref_1
      security: *ref_25
      summary: Get a station by numeric ID
      tags: *ref_26
  /v1/stations/counts_24_hours:
    get:
      description: >-
        Returns a lightweight list of stations, each with its fuzzed location and the number of
        messages received in the last 24 hours. Each item is a computed object: { station_id, ident,
        fuzzed_latitude, fuzzed_longitude, messages_count }.
      operationId: findAllWith24HourMessageCounts
      parameters: []
      responses:
        '200':
          description: >-
            Array of computed objects with station_id, ident, fuzzed_latitude, fuzzed_longitude, and
            messages_count (count as a string).
        '401': *ref_2
        '429': *ref_1
      security: *ref_25
      summary: List stations with 24-hour message counts
      tags: *ref_26
  /v1/stations/ident/{ident}:
    get:
      description: >-
        Returns a single station matching the given ident (human-readable station identifier), or
        null if no station matches.
      operationId: findOne
      parameters:
        - name: ident
          required: true
          in: path
          description: Station ident / identifier.
          schema:
            example: KSEA-1
            type: string
      responses:
        '200':
          description: The matching station, or null if not found.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Station'
        '401': *ref_2
        '429': *ref_1
      security: *ref_25
      summary: Get a station by ident
      tags: *ref_26
  /v1/stations/{id}/coverage:
    get:
      description: >-
        Computes and returns a GeoJSON FeatureCollection describing the station's coverage polygon,
        derived from the locations of messages it received over the selected time window.
      operationId: getStationCoverage
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric station ID (positive integer).
          schema:
            example: 1234
            type: string
        - name: timeFilter
          required: false
          in: query
          description: Time window to analyze. One of '1hour' or '24hours'. Defaults to '24hours'.
          schema:
            enum:
              - 1hour
              - 24hours
            type: string
      responses:
        '200':
          description: GeoJSON FeatureCollection with the coverage polygon.
        '400':
          description: Invalid station ID or invalid time filter.
        '401': *ref_2
        '404':
          description: Station not found.
        '429': *ref_1
      security: *ref_25
      summary: Get station coverage polygon
      tags: *ref_26
  /v1/acars/stats:
    get:
      description: >-
        Returns aggregate ACARS-specific statistics as a key/value object of computed metrics (e.g.
        ACARS message counts).
      operationId: stats
      parameters: []
      responses:
        '200':
          description: Object of computed ACARS statistics keyed by metric name.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AcarsStatsResponseDto'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get ACARS statistics
      tags:
        - Stats
  /v1/airframes/flights/active:
    get:
      description: >-
        Returns currently active flights, served from a short-lived Redis cache when available.
        Requires authentication via JWT or API key. Arbitrary query parameters are passed through as
        filters.
      operationId: findActive
      parameters: []
      responses:
        '200':
          description: An array of active flights.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List active flights
      tags: &ref_27
        - Flights
  /v1/airframes/flights/{id}:
    get:
      description: Returns a single flight by its id. Requires authentication via JWT or API key.
      operationId: findOne
      parameters:
        - name: id
          required: true
          in: path
          description: Flight id.
          schema:
            example: '123456'
            type: string
      responses:
        '200':
          description: The matching flight.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get a flight by id
      tags: *ref_27
  /v1/airframes/flights/bbox/{xmin},{ymin},{xmax},{ymax}:
    get:
      description: >-
        Returns flights whose position falls within the given geographic bounding box. Returns an
        empty array if any bound is infinite. Requires authentication via JWT or API key.
      operationId: findByBoundingBox
      parameters:
        - name: xmin
          required: true
          in: path
          description: Minimum longitude of the bounding box.
          schema:
            example: '-122.5'
            type: string
        - name: ymin
          required: true
          in: path
          description: Minimum latitude of the bounding box.
          schema:
            example: '37.2'
            type: string
        - name: xmax
          required: true
          in: path
          description: Maximum longitude of the bounding box.
          schema:
            example: '-121.8'
            type: string
        - name: ymax
          required: true
          in: path
          description: Maximum latitude of the bounding box.
          schema:
            example: '37.9'
            type: string
      responses:
        '200':
          description: An array of flights within the bounding box.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: List flights within a bounding box
      tags: *ref_27
  /v1/airframes/flights/active/arrdep:
    get:
      description: >-
        Returns active flights that include arrival and departure information. Rate-limited to 100
        requests per 10 seconds.
      operationId: findWithArrDep
      parameters: []
      responses:
        '200':
          description: An array of active flights with arrival/departure data.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '429': *ref_1
      summary: List active flights with arrival/departure data
      tags: *ref_27
  /v1/stats:
    get:
      description: >-
        Returns aggregate platform-wide statistics as a key/value object of computed metrics (e.g.
        message and entity counts).
      operationId: stats
      parameters: []
      responses:
        '200':
          description: Object of computed platform statistics keyed by metric name.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlatformStatsResponseDto'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get platform statistics
      tags:
        - Stats
  /v1/tidbyt/nearby/flights:
    get:
      description: >-
        Returns aircraft currently near a given latitude/longitude within the specified radius,
        formatted for rendering on a Tidbyt display. Results are served from cache when available.
      operationId: nearbyFlights
      parameters:
        - name: radius
          required: true
          in: query
          description: Search radius around the center point, in nautical miles.
          schema:
            example: '25'
        - name: lon
          required: true
          in: query
          description: Longitude of the search center in decimal degrees.
          schema:
            example: '-122.4194'
        - name: lat
          required: true
          in: query
          description: Latitude of the search center in decimal degrees.
          schema:
            example: '37.7749'
      responses:
        '200':
          description: >-
            Nearby flights (with airframe and positions), shaped for consumption by a Tidbyt
            display.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Flight'
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get nearby aircraft for a Tidbyt display
      tags:
        - Tidbyt
  /v1/vdl/stations:
    get:
      description: >-
        Returns all known VDL (VHF Data Link) ground stations as a plain JSON object/array,
        including their ICAO identifiers, network, and associated airport details.
      operationId: findAllStations
      parameters: []
      responses:
        '200':
          description: All VDL ground stations as a serialized JSON object.
        '401': *ref_2
        '429': *ref_1
      security: &ref_28
        - api-key: []
        - bearer: []
      summary: List all VDL ground stations
      tags: &ref_29
        - VDL
  /v1/vdl/stations/geojson:
    get:
      description: >-
        Returns all VDL ground stations as a GeoJSON FeatureCollection. Each feature is a Point at
        the station airport coordinates with properties describing the station and its airport.
      operationId: findAllStationsGeoJSON
      parameters: []
      responses:
        '200':
          description: A GeoJSON FeatureCollection of VDL ground stations (Point features).
        '401': *ref_2
        '429': *ref_1
      security: *ref_28
      summary: List all VDL ground stations as GeoJSON
      tags: *ref_29
  /v1/vdl/stations/{id}:
    get:
      description: >-
        Returns a single VDL ground station identified by its numeric ID as a serialized JSON
        object.
      operationId: findOneStation
      parameters:
        - name: id
          required: true
          in: path
          description: Numeric ID of the VDL ground station.
          schema:
            example: '5'
            type: string
      responses:
        '200':
          description: The VDL ground station with the given ID.
        '401': *ref_2
        '429': *ref_1
      security: *ref_28
      summary: Get a VDL ground station by ID
      tags: *ref_29
  /v1/decode/coverage:
    get:
      operationId: getCoverage
      parameters: []
      responses:
        '200':
          description: Decode coverage summary
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DecodeCoverageResponseDto'
        '401': *ref_2
        '429': *ref_1
      security: &ref_30
        - api-key: []
        - bearer: []
      summary: Overall decode coverage statistics
      tags: &ref_31
        - Decode
  /v1/decode/coverage/labels:
    get:
      operationId: getLabelCoverage
      parameters: []
      responses:
        '200':
          description: Per-label decode coverage
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DecodeLabelCoverageResponseDto'
        '401': *ref_2
        '429': *ref_1
      security: *ref_30
      summary: Per-label decode coverage
      tags: *ref_31
  /v1/decode/positions/recent:
    get:
      operationId: getRecentPositions
      parameters:
        - name: limit
          required: false
          in: query
          description: Max number of positions to return (default 100, max 1000)
          schema:
            example: 100
            type: number
        - name: since
          required: false
          in: query
          description: ISO 8601 timestamp — return only positions after this time
          schema:
            example: '2026-06-05T00:00:00Z'
            type: string
        - name: until
          required: false
          in: query
          description: ISO 8601 timestamp — return only positions before this time
          schema:
            example: '2026-06-08T00:00:00Z'
            type: string
        - name: source_type
          required: false
          in: query
          description: Filter by source type (e.g. acars, vdl, hfdl)
          schema:
            example: acars
            type: string
      responses:
        '200':
          description: Recent decoded positions
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DecodePositionsResponseDto'
        '401': *ref_2
        '429': *ref_1
      security: *ref_30
      summary: Recent decoded positions for map display
      tags: *ref_31
  /v1/leaderboard/v2/meta:
    get:
      description: >-
        Returns metadata describing the available leaderboard datasets (domains, views, categories,
        timeframes and last-updated info). If the data is still being computed, returns { status:
        "computing", message }. Cached for 60 seconds (public).
      operationId: getMeta
      parameters: []
      responses:
        '200':
          description: 'Leaderboard metadata object, or a { status: "computing" } placeholder.'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/LeaderboardMetaDto'
        '401': *ref_2
        '429': *ref_1
      security: &ref_32
        - api-key: []
        - bearer: []
      summary: Get leaderboard metadata
      tags: &ref_33
        - Leaderboard
  /v1/leaderboard/v2/performance/{view}:
    get:
      description: >-
        Returns computed performance data for either stations or users. The view is mapped to its
        plural form (station -> stations, user -> users) internally. Returns an empty object when no
        data is available. Cached for 60 seconds (public).
      operationId: getPerformance
      parameters:
        - name: view
          required: true
          in: path
          description: Which performance view to return. One of 'station' or 'user'.
          schema:
            example: station
            type: string
      responses:
        '200':
          description: Computed performance object, or {} if no data is available.
        '400':
          description: Invalid view value.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get performance leaderboard
      tags: *ref_33
  /v1/leaderboard/v2/hall-of-fame/months:
    get:
      description: >-
        Returns the list of months (YYYY-MM) for which hall-of-fame data is available, as { months:
        string[] }. Cached for 60 seconds (public).
      operationId: getHallOfFameMonths
      parameters: []
      responses:
        '200':
          description: 'Object of the form { months: ["2026-02", ...] }.'
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: List hall-of-fame months
      tags: *ref_33
  /v1/leaderboard/v2/hall-of-fame:
    get:
      description: >-
        Returns the hall-of-fame champions and flounders, optionally for a specific month. When no
        data exists, returns { month, champions: [], flounders: [] }. Cached for 60 seconds
        (public).
      operationId: getHallOfFame
      parameters:
        - name: month
          required: false
          in: query
          description: Month to fetch in YYYY-MM format. Defaults to the most recent month.
          schema:
            example: 2026-02
            type: string
      responses:
        '200':
          description: Hall-of-fame object with champions and flounders for the month.
        '400':
          description: month is not in YYYY-MM format.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get hall of fame
      tags: *ref_33
  /v1/leaderboard/v2/flounders:
    get:
      description: >-
        Returns the current "flounders" picks (lowest performers) as { month, picks: [...] }.
        Returns { month: null, picks: [] } when no data is available. Cached for 60 seconds
        (public).
      operationId: getFlounders
      parameters: []
      responses:
        '200':
          description: Object of the form { month, picks }.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get current flounders
      tags: *ref_33
  /v1/leaderboard/v2/achievements/{userId}:
    get:
      description: >-
        Returns the achievements earned by the given user as { userId, achievements: [...] }.
        Returns an empty achievements array when the user has none or no data exists. Cached for 60
        seconds (public).
      operationId: getAchievements
      parameters:
        - name: userId
          required: true
          in: path
          description: ID of the user whose achievements to fetch.
          schema:
            example: a1b2c3d4-0000-0000-0000-000000000001
            type: string
      responses:
        '200':
          description: Object of the form { userId, achievements }.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get a user's achievements
      tags: *ref_33
  /v1/leaderboard/v2/{domain}/{view}/{category}/{timeframe}:
    get:
      description: >-
        Returns a computed leaderboard ranking for the given domain, view, category and timeframe.
        Valid categories depend on the domain (aircraft: messages/airframes/flights/composite;
        marine: messages/vessels/voyages/composite; combined: messages/entities/tracks/composite).
        Served pre-gzipped from cache when the client supports gzip; otherwise as JSON. Returns a {
        status: "computing" } placeholder when data is not yet ready. Cached for 60 seconds (10
        seconds while computing).
      operationId: getLeaderboard
      parameters:
        - name: domain
          required: true
          in: path
          description: Data domain. One of 'aircraft', 'marine', or 'combined'.
          schema:
            example: aircraft
            type: string
        - name: view
          required: true
          in: path
          description: Ranking subject. One of 'station' or 'user'.
          schema:
            example: station
            type: string
        - name: category
          required: true
          in: path
          description: >-
            Ranking category, valid values depend on the domain (e.g. messages, airframes, flights,
            composite).
          schema:
            example: messages
            type: string
        - name: timeframe
          required: true
          in: path
          description: Ranking timeframe. One of '24h', '30d', or 'all-time'.
          schema:
            example: 30d
            type: string
      responses:
        '200':
          description: 'Computed leaderboard object, or a { status: "computing" } placeholder.'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/LeaderboardResponseDto'
        '400':
          description: Invalid domain, view, category, or timeframe.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get a leaderboard ranking
      tags: *ref_33
  /v1/leaderboard/v2/awards/trigger:
    post:
      description: >-
        Processes (computes and assigns) leaderboard awards for the given month. Pass force=true to
        recompute even if awards already exist for that month. Returns the processing result.
      operationId: triggerAwards
      parameters:
        - name: month
          required: true
          in: query
          description: Month to process in YYYY-MM format.
          schema:
            example: 2026-02
            type: string
        - name: force
          required: false
          in: query
          description: Set to 'true' to force reprocessing even if awards already exist.
          schema:
            example: 'false'
            type: string
      responses:
        '201':
          description: Result of the award processing run.
        '400':
          description: month is missing or not in YYYY-MM format.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Trigger award processing for a month
      tags: *ref_33
  /v1/leaderboard/v2/awards/diagnose-flounders:
    get:
      description: >-
        Returns diagnostic information about how flounder awards are being computed. Pass
        runQueries=true to additionally execute the underlying diagnostic queries.
      operationId: diagnoseFlounders
      parameters:
        - name: runQueries
          required: false
          in: query
          description: Set to 'true' to run the underlying diagnostic queries.
          schema:
            example: 'false'
            type: string
      responses:
        '200':
          description: Diagnostic object describing flounder award computation.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Diagnose flounder award computation
      tags: *ref_33
  /v1/leaderboard/v2/awards/materialize-daily-counts:
    post:
      description: >-
        Recomputes and materializes the daily count data used by award processing. The days
        parameter is clamped to the range 1-60 and defaults to 35.
      operationId: materializeDailyCounts
      parameters:
        - name: days
          required: false
          in: query
          description: Number of days to materialize (clamped between 1 and 60, default 35).
          schema:
            example: '35'
            type: string
      responses:
        '201':
          description: Result of the materialization run.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Materialize daily counts for awards
      tags: *ref_33
  /v1/leaderboard/current:
    get:
      description: >-
        Legacy backward-compatibility endpoint. Returns the aircraft/station/messages/30d
        leaderboard reshaped into the historical { current, next, previous } format. Prefer the v2
        endpoints for new integrations. Cached for 60 seconds (public).
      operationId: legacyCurrent
      parameters: []
      responses:
        '200':
          description: Legacy-shaped leaderboard object with current, next, and previous fields.
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get current leaderboard (legacy)
      tags: *ref_33
  /v1/leaderboard/{date}:
    get:
      description: >-
        Legacy backward-compatibility endpoint. The date parameter is ignored; this always returns
        the same data as the current legacy leaderboard. Prefer the v2 endpoints for new
        integrations. Cached for 60 seconds (public).
      operationId: legacyDate
      parameters:
        - name: date
          required: true
          in: path
          description: Date parameter (ignored, retained for backward compatibility).
          schema:
            example: '2026-02-14'
            type: string
      responses:
        '200':
          description: Legacy-shaped leaderboard object (same as /leaderboard/current).
        '401': *ref_2
        '429': *ref_1
      security: *ref_32
      summary: Get leaderboard by date (legacy)
      tags: *ref_33
  /v1/stats/frequency-usage:
    get:
      description: >-
        Returns aggregated frequency usage statistics for the requested period, optionally filtered
        by protocol and country. Results can be limited via the limit parameter. Cached for 60
        seconds (public).
      operationId: getUsage
      parameters:
        - name: protocol
          required: false
          in: query
          description: Filter by protocol (case-insensitive, e.g. acars, vdl2, hfdl).
          schema:
            example: acars
            type: string
        - name: country
          required: false
          in: query
          description: Filter by 2- or 3-character country code (or 'ZZ'). Case-insensitive.
          schema:
            example: US
            type: string
        - name: limit
          required: false
          in: query
          description: Maximum number of rows to return (clamped between 1 and 1000, default 250).
          schema:
            example: '250'
            type: string
        - name: period
          required: false
          in: query
          description: Aggregation period. One of 'day', 'week', 'month', or 'year'. Defaults to 'day'.
          schema:
            example: day
      responses:
        '200':
          description: Aggregated frequency usage statistics for the selected period and filters.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FrequencyUsageResponseDto'
        '400':
          description: Invalid period or invalid country code.
        '401': *ref_2
        '429': *ref_1
      security:
        - api-key: []
        - bearer: []
      summary: Get frequency usage statistics
      tags:
        - Stats
info:
  title: Airframes API
  description: >-
    Aviation data — ACARS, VDL, HFDL and SATCOM messages, flights, airframes, airlines, airports and
    station telemetry — aggregated and processed by Airframes, supported by a global network of
    community feeder stations.


    All endpoints are served under the `/v1` prefix (e.g. `https://api.airframes.io/v1/flights`).
    For backward compatibility the same endpoints also respond without the prefix, but `/v1` is the
    documented, stable path and should be preferred.


    **Pagination** — list endpoints accept `limit`/`offset` (or `page`/`limit`, or cursor
    `before_id`) and return pagination metadata in response headers: `X-Total-Count` (when known),
    `X-Result-Count`, and `X-Page`/`X-Per-Page`/`X-Total-Pages` for paged endpoints.


    **Time ranges** — time-filtered list endpoints accept `since` and `until` (ISO-8601).


    **Rate limits** — responses carry `X-RateLimit-Limit`, `X-RateLimit-Remaining` and
    `X-RateLimit-Reset` (and `Retry-After` on 429). Every response includes an `X-Request-ID` for
    support.
  version: '1.0'
  contact:
    name: Airframes
    url: https://airframes.io/
    email: kevin@airframes.io
  termsOfService: https://docs.airframes.io/api/terms
tags: []
servers:
  - url: https://api.airframes.io
    description: Production
  - url: https://staging.airframes.io
    description: Staging
components:
  securitySchemes:
    bearer:
      scheme: bearer
      bearerFormat: JWT
      type: http
      description: Airframes API key as a bearer token (af_...)
    api-key:
      type: apiKey
      in: header
      name: x-api-key
  schemas:
    RegisterDto:
      type: object
      properties: {}
    ConfirmDto:
      type: object
      properties: {}
    ResendConfirmationDto:
      type: object
      properties: {}
    ResetPasswordDto:
      type: object
      properties: {}
    ResetPasswordConfirmDto:
      type: object
      properties: {}
    DecodeAcarsDto:
      type: object
      properties:
        label:
          type: string
          description: ACARS label identifying the message type to decode.
          example: H1
        text:
          type: string
          description: Raw ACARS message text to decode.
          example: '#DFB/PIREP...'
      required:
        - label
        - text
    UpdateSponsorDto:
      type: object
      properties: {}
    LeaderboardRank:
      type: object
      properties: {}
    StationMessageCount:
      type: object
      properties:
        id:
          type: number
          description: Auto-generated primary key for the count record.
          example: 42
        station:
          description: Station this aggregate count belongs to.
          allOf:
            - $ref: '#/components/schemas/Station'
        stationId:
          type: number
          description: ID of the station this count belongs to.
          example: 1234
        messagesCount:
          type: number
          description: Total lifetime number of messages received by the station.
          example: 1582940
      required:
        - id
        - stationId
        - messagesCount
    User:
      type: object
      properties: {}
    Station:
      type: object
      properties:
        id:
          type: number
          description: Auto-generated primary key for the station.
          example: 1234
        uuid:
          type: string
          description: Stable UUID identifying the station across systems.
          example: b3c1e2f4-5a6b-4c7d-8e9f-0a1b2c3d4e5f
        ident:
          type: string
          description: Human-readable station identifier (callsign/handle).
          example: KSEA-1
        type:
          type: string
          description: Station type classification.
          example: ground
        ipAddress:
          type: string
          description: Source IP address of the station. Masked when serialized to API consumers.
          example: 203.0.113.0
        leaderboardRanks:
          description: Leaderboard rank rows associated with this station.
          type: array
          items:
            $ref: '#/components/schemas/LeaderboardRank'
        messages:
          description: Messages received by this station.
          type: array
          items:
            $ref: '#/components/schemas/Message'
        stationMessageCount:
          description: Aggregated lifetime message count record for this station.
          allOf:
            - $ref: '#/components/schemas/StationMessageCount'
        messagesCount:
          type: number
          description: Lifetime message count, hydrated from stationMessageCount after load.
          example: 1582940
        airframes:
          description: Airframes this station has received messages from.
          type: array
          items:
            $ref: '#/components/schemas/Airframe'
        sourceApplication:
          type: string
          description: Application that produced the station feed.
          example: acarsdec
        sourceType:
          type: string
          description: Source data type for the station feed.
          example: acars
        sourceProtocol:
          type: string
          description: Source protocol used to deliver messages.
          example: udp
        userId:
          type: string
          description: ID of the user that owns this station.
          example: a1b2c3d4-0000-0000-0000-000000000001
        user:
          description: Owning user. Sensitive fields are stripped before serialization.
          allOf:
            - $ref: '#/components/schemas/User'
        latitude:
          type: string
          description: >-
            Effective latitude served to clients (resolved in afterLoad from user/geoip/fuzzed
            source).
          example: '47.4502'
        longitude:
          type: string
          description: >-
            Effective longitude served to clients (resolved in afterLoad from user/geoip/fuzzed
            source).
          example: '-122.3088'
        geoipLatitude:
          type: string
          description: Latitude derived from GeoIP lookup of the station IP.
          example: '47.4502'
        geoipLongitude:
          type: string
          description: Longitude derived from GeoIP lookup of the station IP.
          example: '-122.3088'
        userLatitude:
          type: string
          description: Latitude explicitly provided by the station owner.
          example: '47.4502'
        userLongitude:
          type: string
          description: Longitude explicitly provided by the station owner.
          example: '-122.3088'
        fuzzedLatitude:
          type: string
          description: Privacy-fuzzed latitude used when use_fuzzed_location is enabled.
          example: '47.45'
        fuzzedLongitude:
          type: string
          description: Privacy-fuzzed longitude used when use_fuzzed_location is enabled.
          example: '-122.31'
        useFuzzedLocation:
          type: boolean
          description: Whether the fuzzed (privacy) location should be used instead of exact coordinates.
          example: false
        altitude:
          type: number
          description: Antenna altitude in meters above sea level.
          example: 120
        nearestAirportIcao:
          type: string
          description: ICAO code of the airport nearest to the station.
          example: KSEA
        description:
          type: string
          description: Free-text description of the station.
          example: Rooftop ACARS receiver near Seattle
        systemPlatform:
          type: string
          description: Hardware/system platform the station runs on.
          example: Raspberry Pi 4
        systemOS:
          type: string
          description: Operating system the station runs.
          example: DietPi (Debian 12)
        equipmentSdr:
          type: string
          description: SDR hardware used by the station.
          example: RTL-SDR Blog V3
        equipmentFilters:
          type: string
          description: RF filters in the receive chain.
          example: FlightAware 1090 MHz bandpass
        equipmentAntenna:
          type: string
          description: Antenna used by the station.
          example: Discone 25-1300 MHz
        countryCode:
          type: string
          description: ISO 3166-1 country code of the station location.
          example: US
        countryName:
          type: string
          description: Country name of the station location.
          example: United States
        flagEmoji:
          type: string
          description: Emoji flag for the station country.
          example: 🇺🇸
        flagImageUrl:
          type: string
          description: URL to a flag image for the station country.
          example: https://airframes.io/flags/us.svg
        status:
          type: string
          description: Current station status.
          example: active
        flagged:
          type: boolean
          description: Whether the station has been flagged for review.
          example: false
          default: false
        flaggedReason:
          type: string
          description: Reason the station was flagged, if any.
          example: Suspected spoofed positions
          nullable: true
        flaggedAt:
          format: date-time
          type: string
          description: Timestamp the station was flagged, if any.
          example: '2026-02-14T08:30:00.000Z'
          nullable: true
        blocked:
          type: boolean
          description: Whether the station is blocked from feeding data.
          example: false
          default: false
        lastReportAt:
          format: date-time
          type: string
          description: Timestamp of the most recent report from the station.
          example: '2026-06-05T12:00:00.000Z'
        createdAt:
          format: date-time
          type: string
          description: Timestamp the station record was created.
          example: '2025-01-10T09:15:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp the station record was last updated.
          example: '2026-06-05T12:00:00.000Z'
        circles:
          type: object
          description: >-
            GeoJSON FeatureCollection of range-ring coverage circles (50/100/150/200nm), populated
            on single-station lookups.
        coverage:
          type: object
          description: GeoJSON coverage polygon, populated on single-station lookups.
        polarCoverage:
          type: object
          description: Polar histogram of coverage by bearing (currently unused / reserved).
        recentMessages:
          description: Recent messages associated with the station, when included.
          type: array
          items:
            type: array
      required:
        - id
        - uuid
        - ident
        - type
        - ipAddress
        - sourceApplication
        - sourceType
        - sourceProtocol
        - userId
        - useFuzzedLocation
        - altitude
        - nearestAirportIcao
        - description
        - systemPlatform
        - systemOS
        - equipmentSdr
        - equipmentFilters
        - equipmentAntenna
        - countryCode
        - countryName
        - flagEmoji
        - flagImageUrl
        - status
        - flagged
        - blocked
        - createdAt
        - updatedAt
    Airline:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated database ID of the airline.
          example: '42'
        airframes:
          description: Airframes owned or operated by this airline.
          type: array
          items:
            $ref: '#/components/schemas/Airframe'
        flights:
          description: Flights operated by this airline.
          type: array
          items:
            $ref: '#/components/schemas/Flight'
        name:
          type: string
          description: Airline name.
          example: United Airlines
        icao:
          type: string
          description: ICAO airline code (3 letters).
          example: UAL
        iata:
          type: string
          description: IATA airline code (2 characters).
          example: UA
        prefix:
          type: string
          description: Airline accounting/numeric prefix code.
          example: '016'
        callsign:
          type: string
          description: Radio telephony callsign of the airline.
          example: UNITED
        addressLine1:
          type: string
          description: First line of the airline mailing address.
          example: 233 S Wacker Dr
        addressLine2:
          type: string
          description: Second line of the airline mailing address.
          example: Willis Tower
        city:
          type: string
          description: City of the airline address.
          example: Chicago
        region:
          type: string
          description: State or region of the airline address.
          example: Illinois
        country:
          type: string
          description: Country of the airline address.
          example: United States
        postalCode:
          type: string
          description: Postal/ZIP code of the airline address.
          example: '60606'
        phoneCountryCode:
          type: string
          description: Phone country dialing code.
          example: '+1'
        phone:
          type: string
          description: Contact phone number.
          example: 800-864-8331
        email:
          type: string
          description: Contact email address.
          example: contact@united.com
        logoUrl:
          type: string
          description: URL of the airline logo image.
          example: https://example.com/logos/ual.png
        websiteUrl:
          type: string
          description: Airline website URL.
          example: https://www.united.com
        facebookUrl:
          type: string
          description: Airline Facebook page URL.
          example: https://www.facebook.com/United
        youtubeUrl:
          type: string
          description: Airline YouTube channel URL.
          example: https://www.youtube.com/user/united
        linkedinUrl:
          type: string
          description: Airline LinkedIn page URL.
          example: https://www.linkedin.com/company/united-airlines
        instagramUrl:
          type: string
          description: Airline Instagram profile URL.
          example: https://www.instagram.com/united
        avCodesId:
          type: string
          description: External AvCodes reference ID for this airline.
          example: UAL-001
      required:
        - id
        - name
        - icao
        - iata
        - prefix
        - callsign
        - addressLine1
        - addressLine2
        - city
        - region
        - country
        - postalCode
        - phoneCountryCode
        - phone
        - email
        - logoUrl
        - websiteUrl
        - facebookUrl
        - youtubeUrl
        - linkedinUrl
        - instagramUrl
        - avCodesId
    FlightEvent:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated flight event id.
          example: '987654'
        eventAt:
          format: date-time
          type: string
          description: Timestamp at which the event occurred.
          example: '2026-06-05T15:30:00.000Z'
        code:
          type: string
          description: Event code identifying what happened.
          example: TAKEOFF
        flight:
          description: Flight this event belongs to.
          allOf:
            - $ref: '#/components/schemas/Flight'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the event record was created.
          example: '2026-06-05T15:30:01.000Z'
      required:
        - id
        - eventAt
        - code
        - createdAt
    FlightPosition:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated position id. Excluded from serialized API responses.
          example: '5551234'
        flight:
          description: Flight this position belongs to.
          allOf:
            - $ref: '#/components/schemas/Flight'
        latitude:
          type: string
          description: Latitude of the position, in decimal degrees.
          example: '37.6213'
        longitude:
          type: string
          description: Longitude of the position, in decimal degrees.
          example: '-122.3790'
        altitude:
          type: number
          description: Altitude of the position, in feet.
          example: 35000
        track:
          type: string
          description: Ground track / heading at this position, in degrees.
          example: '271'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the position was recorded.
          example: '2026-06-05T15:45:00.000Z'
      required:
        - id
        - latitude
        - longitude
        - altitude
        - track
        - createdAt
    Flight:
      type: object
      properties:
        id:
          type: number
          description: Auto-generated numeric flight id.
          example: 123456
        flight:
          type: string
          description: Normalized flight identifier / callsign.
          example: UAL123
        flightIcao:
          type: string
          description: ICAO-format flight number.
          example: UAL123
        flightIata:
          type: string
          description: IATA-format flight number.
          example: UA123
        designator:
          type: string
          description: Airline designator portion of the flight identifier.
          example: UAL
        number:
          type: number
          description: Numeric portion of the flight identifier.
          example: 123
        airframe:
          description: Airframe (aircraft) associated with this flight.
          allOf:
            - $ref: '#/components/schemas/Airframe'
        airline:
          description: Airline operating this flight.
          allOf:
            - $ref: '#/components/schemas/Airline'
        events:
          description: Events recorded for this flight.
          type: array
          items:
            $ref: '#/components/schemas/FlightEvent'
        messages:
          description: Messages associated with this flight.
          type: array
          items:
            $ref: '#/components/schemas/Message'
        status:
          type: string
          description: Current flight status.
          example: in-flight
        departingAirport:
          type: string
          description: ICAO code of the departure airport.
          example: KSFO
        departureTimeScheduled:
          format: date-time
          type: string
          description: Scheduled departure time.
          example: '2026-06-05T14:30:00.000Z'
        departureTimeActual:
          format: date-time
          type: string
          description: Actual departure time.
          example: '2026-06-05T14:42:00.000Z'
        departureGateScheduled:
          type: string
          description: Scheduled departure gate.
          example: B12
        departureGateActual:
          type: string
          description: Actual departure gate.
          example: B14
        destinationAirport:
          type: string
          description: ICAO code of the destination airport.
          example: KORD
        arrivalTimeScheduled:
          format: date-time
          type: string
          description: Scheduled arrival time.
          example: '2026-06-05T18:15:00.000Z'
        arrivalTimeActual:
          format: date-time
          type: string
          description: Actual arrival time.
          example: '2026-06-05T18:09:00.000Z'
        arrivalGateScheduled:
          type: string
          description: Scheduled arrival gate.
          example: C7
        arrivalGateActual:
          type: string
          description: Actual arrival gate.
          example: C9
        latitude:
          type: string
          description: Last known latitude, in decimal degrees.
          example: '37.6213'
        longitude:
          type: string
          description: Last known longitude, in decimal degrees.
          example: '-122.3790'
        altitude:
          type: number
          description: Last known altitude, in feet.
          example: 35000
        track:
          type: number
          description: Last known ground track / heading, in degrees.
          example: 271
        positions:
          description: Recorded positions for this flight.
          type: array
          items:
            $ref: '#/components/schemas/FlightPosition'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the flight record was created.
          example: '2026-06-05T14:00:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the flight record was last updated.
          example: '2026-06-05T18:09:00.000Z'
      required:
        - id
        - flight
        - flightIcao
        - flightIata
        - designator
        - number
        - status
        - createdAt
        - updatedAt
    Message:
      type: object
      properties:
        id:
          type: number
          description: Auto-generated numeric primary key for the message.
          example: 123456
        station:
          description: The receiving station (feeder) that captured this message, if associated.
          allOf:
            - $ref: '#/components/schemas/Station'
        airframe:
          description: The airframe (aircraft) this message is associated with, if resolved.
          allOf:
            - $ref: '#/components/schemas/Airframe'
        flight:
          description: The flight this message is associated with, if resolved.
          allOf:
            - $ref: '#/components/schemas/Flight'
        source:
          type: string
          description: Identifier of the source/feeder that produced this message.
          example: feed.airframes.io
        sourceType:
          type: string
          description: Type of the source link/decoder (e.g. acars, vdl, hfdl, satcom).
          example: acars
        linkDirection:
          type: string
          description: Direction of the message on the datalink (e.g. uplink or downlink).
          example: downlink
        fromHex:
          type: string
          description: Source (originating) address in hexadecimal, when present.
          example: A1B2C3
        toHex:
          type: string
          description: Destination address in hexadecimal, when present.
          example: D4E5F6
        timestamp:
          format: date-time
          type: string
          description: Timestamp at which the message was received/decoded.
          example: '2026-06-05T12:34:56.000Z'
        tail:
          type: string
          description: Aircraft tail (registration) number.
          example: N12345
        flightNumber:
          type: string
          description: Flight number/identifier carried in the message (stored in the "flight" column).
          example: UAL123
        channel:
          type: number
          description: Channel number on which the message was received.
          example: 1
        frequency:
          type: string
          description: Frequency (in MHz) on which the message was received.
          example: '131.550'
        level:
          type: number
          description: Signal level of the received message, in dBm.
          example: -24
        error:
          type: number
          description: Number of decode errors detected in the message.
          example: 0
        mode:
          type: string
          description: ACARS mode character.
          example: '2'
        label:
          type: string
          description: ACARS label identifying the message type.
          example: H1
        blockId:
          type: string
          description: ACARS block identifier.
          example: '4'
        messageNumber:
          type: string
          description: ACARS message sequence number.
          example: M01A
        ack:
          type: string
          description: Acknowledgement field from the ACARS frame.
          example: NAK
        data:
          type: string
          description: Raw message data payload.
          example: '#DFB/PIREP...'
        text:
          type: string
          description: Decoded human-readable message text.
          example: POSITION REPORT N4012.5 W07400.3
        departingAirport:
          type: string
          description: Departing airport, when present in the message.
          example: KSFO
        destinationAirport:
          type: string
          description: Destination airport, when present in the message.
          example: KJFK
        latitude:
          type: number
          description: Decoded latitude, when present in the message.
          example: 37.6189
        longitude:
          type: number
          description: Decoded longitude, when present in the message.
          example: -122.375
        altitude:
          type: number
          description: Decoded altitude (in feet), when present in the message.
          example: 35000
        uuid:
          type: string
          description: UUID assigned to this message by the producing source.
          example: 550e8400-e29b-41d4-a716-446655440000
        arUUID:
          type: string
          description: Airframes-assigned UUID (ar_uuid) for this message.
          example: 7c9e6679-7425-40de-944b-e07fc1f90ae7
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the record was created.
          example: '2026-06-05T12:34:57.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the record was last updated.
          example: '2026-06-05T12:34:57.000Z'
      required:
        - id
        - source
        - sourceType
        - linkDirection
        - fromHex
        - toHex
        - timestamp
        - tail
        - flightNumber
        - channel
        - frequency
        - level
        - error
        - mode
        - label
        - blockId
        - messageNumber
        - ack
        - data
        - text
        - departingAirport
        - destinationAirport
        - latitude
        - longitude
        - altitude
        - uuid
        - arUUID
        - createdAt
        - updatedAt
    Airframe:
      type: object
      properties:
        id:
          type: number
          description: Auto-generated numeric database ID of the airframe.
          example: 12345
        tail:
          type: string
          description: Tail (registration) number of the aircraft.
          example: N12345
        icao:
          type: string
          description: ICAO code / 24-bit address of the aircraft.
          example: A12B34
        iata:
          type: string
          description: IATA code associated with the aircraft.
          example: '320'
        icaoType:
          type: string
          description: ICAO aircraft type designator.
          example: A320
        description:
          type: string
          description: Human-readable description of the aircraft.
          example: Airbus A320-214
        manufacturer:
          type: string
          description: Aircraft manufacturer.
          example: Airbus
        manufacturerModel:
          type: string
          description: Manufacturer model designation.
          example: A320-214
        owner:
          type: string
          description: Registered owner or operator of the aircraft.
          example: United Airlines
        messages:
          description: Messages received from this airframe.
          type: array
          items:
            $ref: '#/components/schemas/Message'
        messagesCount:
          type: number
          description: Computed count of messages received from this airframe, when populated.
          example: 10523
        airline:
          description: Airline that owns or operates this airframe.
          allOf:
            - $ref: '#/components/schemas/Airline'
        flights:
          description: Flights flown by this airframe.
          type: array
          items:
            $ref: '#/components/schemas/Flight'
        stations:
          description: Ground stations that have received messages from this airframe.
          type: array
          items:
            $ref: '#/components/schemas/Station'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the airframe record was created.
          example: '2024-01-15T08:30:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the airframe record was last updated.
          example: '2024-03-22T14:05:00.000Z'
      required:
        - id
        - tail
        - icao
        - iata
        - icaoType
        - description
        - manufacturer
        - manufacturerModel
        - owner
        - createdAt
        - updatedAt
    RouteAirportDto:
      type: object
      properties:
        icao:
          type: string
          description: Airport ICAO code.
          example: KSFO
        ident:
          type: string
          description: OurAirports ident.
          example: KSFO
        name:
          type: string
          description: Airport name.
          example: San Francisco International Airport
        latitude:
          type: number
          description: Latitude in decimal degrees.
          example: 37.6188
        longitude:
          type: number
          description: Longitude in decimal degrees.
          example: -122.3756
      required:
        - icao
        - latitude
        - longitude
    RoutePointDto:
      type: object
      properties:
        latitude:
          type: number
          description: Latitude in decimal degrees.
          example: 37.6188
        longitude:
          type: number
          description: Longitude in decimal degrees.
          example: -122.3756
        altitude:
          type: number
          description: Altitude in feet, when known (flown points only).
          example: 35000
          nullable: true
        track:
          type: number
          description: Track/heading in degrees, when known (flown points only).
          example: 92
          nullable: true
        timestamp:
          type: string
          description: ISO-8601 timestamp of the point, when known (flown points).
          example: '2026-06-08T12:34:56.000Z'
          nullable: true
        name:
          type: string
          description: Named waypoint/fix, when known (filed routes only).
          example: KSFO
          nullable: true
      required:
        - latitude
        - longitude
    GreatCircleRouteResponseDto:
      type: object
      properties:
        from:
          description: Departure airport.
          allOf:
            - $ref: '#/components/schemas/RouteAirportDto'
        to:
          description: Destination airport.
          allOf:
            - $ref: '#/components/schemas/RouteAirportDto'
        distanceNm:
          type: number
          description: Great-circle distance in nautical miles.
          example: 2235.4
        initialBearing:
          type: number
          description: Initial true bearing in degrees (0–360).
          example: 273.1
        pointCount:
          type: number
          description: Number of points returned.
          example: 65
        points:
          description: Interpolated great-circle points (departure → destination).
          type: array
          items:
            $ref: '#/components/schemas/RoutePointDto'
      required:
        - from
        - to
        - distanceNm
        - initialBearing
        - pointCount
        - points
    FlightRouteResponseDto:
      type: object
      properties:
        flightId:
          type: number
          description: Flight id.
          example: 5544014689
        source:
          type: string
          description: >-
            Where the route came from: `flown` = actual ADS-B track from positions; `great_circle` =
            synthesized departure→destination great-circle line (no positions available); `none` =
            no route could be derived.
          enum:
            - flown
            - great_circle
            - none
          example: flown
        departure:
          type: string
          description: Departure airport ICAO, when known.
          example: KSFO
          nullable: true
        destination:
          type: string
          description: Destination airport ICAO, when known.
          example: KJFK
          nullable: true
        distanceNm:
          type: number
          description: Total route distance in nautical miles.
          example: 2235.4
          nullable: true
        pointCount:
          type: number
          description: Number of points in the route.
          example: 128
        points:
          description: Ordered route points.
          type: array
          items:
            $ref: '#/components/schemas/RoutePointDto'
      required:
        - flightId
        - source
        - pointCount
        - points
    LivePositionDto:
      type: object
      properties:
        lat:
          type: number
          description: Latitude in decimal degrees.
          example: 37.6188
        lon:
          type: number
          description: Longitude in decimal degrees.
          example: -122.3754
        alt:
          type: number
          description: Altitude in feet, when known.
          example: 35000
        speed:
          type: number
          description: Ground speed in knots, when known.
          example: 420
        heading:
          type: number
          description: Magnetic heading in degrees (0–359), when known.
          example: 270
        track:
          type: number
          description: Track over ground in degrees (0–359), when known.
          example: 268
        timestamp:
          type: number
          description: Observation timestamp in epoch milliseconds.
          example: 1717459200000
        source:
          type: string
          description: Source that produced this position (e.g. the ingest feed).
          example: adsb
        confidence:
          type: string
          description: Confidence in the position (e.g. low, medium, high).
          example: high
        type:
          type: string
          description: Position type (e.g. observed, estimated).
          example: observed
      required:
        - lat
        - lon
        - timestamp
        - source
        - confidence
        - type
    LiveFlightDto:
      type: object
      properties:
        cacheId:
          type: string
          description: Entity cache ID of the live flight.
          example: A1B2C3
        transport:
          type: string
          description: Transport type of the entity (e.g. aircraft).
          example: aircraft
        hex:
          type: string
          description: ICAO 24-bit hex code of the aircraft.
          example: a1b2c3
        tail:
          type: string
          description: Tail / registration of the aircraft.
          example: N12345
        flightIcao:
          type: string
          description: ICAO flight number / callsign.
          example: SWA403
        flightIata:
          type: string
          description: IATA flight number.
          example: WN403
        flightRaw:
          type: string
          description: Raw flight callsign as decoded.
          example: SWA403
        departure:
          type: string
          description: Departure airport ICAO code.
          example: KLAX
        arrival:
          type: string
          description: Arrival airport ICAO code.
          example: KSFO
        status:
          type: string
          description: Entity status (e.g. active, gapped, ended).
          example: active
        source:
          type: string
          description: Last ingest source for the entity.
          example: adsb
        airframeId:
          type: string
          description: Airframe DB ID, if the entity has been synced.
          example: '987654'
        dbId:
          type: string
          description: Flight DB ID, if the entity has been synced.
          example: '123456'
        firstSeenAt:
          type: number
          description: First seen timestamp in epoch seconds.
          example: 1717459000
        lastSeenAt:
          type: number
          description: Last seen timestamp in epoch seconds.
          example: 1717459200
        position:
          description: Current position of the flight, or null if no position is available.
          nullable: true
          allOf:
            - $ref: '#/components/schemas/LivePositionDto'
        trailCount:
          type: number
          description: Number of trail points recorded for this flight.
          example: 42
        trail:
          description: >-
            Full position trail. Only populated by the single-flight endpoint (GET
            /flights/live/:cacheId).
          type: array
          items:
            $ref: '#/components/schemas/LivePositionDto'
      required:
        - cacheId
        - transport
    Airport:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated UUID of the airport.
          example: 6c2e9f1a-1b2c-4d3e-8f9a-0b1c2d3e4f5a
        name:
          type: string
          description: Airport name.
          example: San Francisco International Airport
        type:
          type: string
          description: Airport type.
          example: large_airport
        ident:
          type: string
          description: Airport ident code (OurAirports identifier).
          example: KSFO
        icao:
          type: string
          description: ICAO airport code (4 letters).
          example: KSFO
        iata:
          type: string
          description: IATA airport code (3 letters).
          example: SFO
        municipality:
          type: string
          description: Municipality (city) the airport serves.
          example: San Francisco
        region:
          type: string
          description: State or region where the airport is located.
          example: California
        country:
          type: string
          description: Country where the airport is located.
          example: United States
        countryCode:
          type: string
          description: ISO country code.
          example: US
        latitude:
          type: number
          description: Latitude of the airport in decimal degrees.
          example: 37.6188
        longitude:
          type: number
          description: Longitude of the airport in decimal degrees.
          example: -122.375
        altitude:
          type: number
          description: Field elevation / altitude of the airport in feet.
          example: 13
        faaLid:
          type: string
          description: FAA Location Identifier (LID).
          example: SFO
        ourAirportId:
          type: string
          description: OurAirports source record ID.
          example: '3469'
        status:
          type: string
          description: Operational status of the airport.
          example: active
        frequencies:
          description: Radio frequencies associated with this airport.
          type: array
          items:
            $ref: '#/components/schemas/AirportFrequency'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the airport record was created.
          example: '2024-01-15T08:30:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the airport record was last updated.
          example: '2024-03-22T14:05:00.000Z'
      required:
        - id
        - name
        - type
        - ident
        - icao
        - iata
        - municipality
        - region
        - country
        - countryCode
        - latitude
        - longitude
        - altitude
        - faaLid
        - ourAirportId
        - status
        - createdAt
        - updatedAt
    AirportFrequencyFeed:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated database ID of the frequency feed.
          example: '5001'
        frequency:
          description: Airport frequency this feed belongs to.
          allOf:
            - $ref: '#/components/schemas/AirportFrequency'
        type:
          type: string
          description: Type of the feed (e.g. the audio stream source/provider).
          example: liveatc
        status:
          type: string
          description: Operational status of the feed.
          example: active
        url:
          type: string
          description: URL of the live audio stream feed.
          example: https://www.liveatc.net/play/ksfo_twr.pls
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the feed record was created.
          example: '2024-01-15T08:30:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the feed record was last updated.
          example: '2024-03-22T14:05:00.000Z'
      required:
        - id
        - type
        - status
        - url
        - createdAt
        - updatedAt
    AirportFrequency:
      type: object
      properties:
        id:
          type: string
          description: Auto-generated database ID of the airport frequency.
          example: '1001'
        airportIdent:
          type: string
          description: Ident code of the airport this frequency belongs to.
          example: KSFO
        airport:
          description: Airport this frequency belongs to.
          allOf:
            - $ref: '#/components/schemas/Airport'
        type:
          type: string
          description: Type of the frequency (e.g. tower, ground, ATIS).
          example: TWR
        frequency:
          type: string
          description: Frequency value in MHz.
          example: '120.500'
        ourAirportsId:
          type: number
          description: OurAirports source record ID for this frequency.
          example: 12345
        description:
          type: string
          description: Human-readable description of the frequency.
          example: San Francisco Tower
        status:
          type: string
          description: Operational status of the frequency.
          example: active
        feeds:
          description: Live audio feeds available for this frequency.
          type: array
          items:
            $ref: '#/components/schemas/AirportFrequencyFeed'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the frequency record was created.
          example: '2024-01-15T08:30:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the frequency record was last updated.
          example: '2024-03-22T14:05:00.000Z'
      required:
        - id
        - airportIdent
        - type
        - frequency
        - ourAirportsId
        - description
        - status
        - createdAt
        - updatedAt
    MarineVoyagePosition:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the voyage position report.
          example: '987654'
        vessel:
          description: The vessel that reported this position.
          allOf:
            - $ref: '#/components/schemas/MarineVessel'
        voyage:
          description: The voyage this position report belongs to.
          allOf:
            - $ref: '#/components/schemas/MarineVoyage'
        message:
          description: The AIS message this position was derived from.
          allOf:
            - $ref: '#/components/schemas/MarineMessage'
        latitude:
          type: string
          description: Latitude of the reported position (decimal degrees).
          example: '30.5852'
        longitude:
          type: string
          description: Longitude of the reported position (decimal degrees).
          example: '32.3286'
        rateOfTurn:
          type: number
          description: Rate of turn in degrees per minute (positive = turning to starboard).
          example: 0
        speedOverGround:
          type: number
          description: Speed over ground in knots.
          example: 12.3
        courseOverGround:
          type: number
          description: Course over ground in degrees (0-359).
          example: 187.5
        trueHeading:
          type: number
          description: True heading of the vessel in degrees (0-359).
          example: 188
        positionAccuracy:
          type: boolean
          description: Position accuracy flag (true = high accuracy, e.g. DGPS within 10m).
          example: true
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the position report was recorded.
          example: '2024-06-01T11:58:00.000Z'
      required:
        - id
        - latitude
        - longitude
        - createdAt
    MarineVoyage:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the voyage.
          example: '67890'
        vessel:
          description: The vessel associated with this voyage.
          allOf:
            - $ref: '#/components/schemas/MarineVessel'
        messages:
          description: AIS messages received during this voyage.
          type: array
          items:
            $ref: '#/components/schemas/MarineMessage'
        positions:
          description: Position reports recorded during this voyage.
          type: array
          items:
            $ref: '#/components/schemas/MarineVoyagePosition'
        lastPosition:
          description: The most recent position report for this voyage.
          allOf:
            - $ref: '#/components/schemas/MarineVoyagePosition'
        lastHeardAt:
          format: date-time
          type: string
          description: Timestamp when the vessel was last heard on this voyage.
          example: '2024-06-01T11:58:00.000Z'
        lastLatitude:
          type: string
          description: Latitude of the last reported position (decimal degrees).
          example: '30.5852'
        lastLongitude:
          type: string
          description: Longitude of the last reported position (decimal degrees).
          example: '32.3286'
        status:
          type: string
          description: Current status of the voyage.
          example: active
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the voyage record was created.
          example: '2024-05-20T06:00:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the voyage record was last updated.
          example: '2024-06-01T12:00:00.000Z'
      required:
        - id
        - lastHeardAt
        - lastLatitude
        - lastLongitude
        - status
        - createdAt
        - updatedAt
    MarineMessage:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the AIS message.
          example: '5551234'
        vessel:
          description: The vessel that transmitted this AIS message.
          allOf:
            - $ref: '#/components/schemas/MarineVessel'
        voyage:
          description: The voyage this AIS message is associated with.
          allOf:
            - $ref: '#/components/schemas/MarineVoyage'
        stationId:
          type: string
          description: Identifier of the ground station that received the message.
          example: KX1ABC
        timestamp:
          format: date-time
          type: string
          description: Timestamp of the AIS message as reported by the source.
          example: '2024-06-01T11:58:00.000Z'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the message record was created.
          example: '2024-06-01T11:58:01.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the message record was last updated.
          example: '2024-06-01T11:58:01.000Z'
      required:
        - id
        - createdAt
        - updatedAt
    MarineVessel:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the vessel.
          example: '12345'
        messages:
          description: AIS messages received from this vessel.
          type: array
          items:
            $ref: '#/components/schemas/MarineMessage'
        voyages:
          description: Voyages tracked for this vessel.
          type: array
          items:
            $ref: '#/components/schemas/MarineVoyage'
        mmsiNumber:
          type: string
          description: Maritime Mobile Service Identity (MMSI) number of the vessel.
          example: '366998410'
        imoNumber:
          type: string
          description: International Maritime Organization (IMO) number of the vessel.
          example: '9395044'
        callsign:
          type: string
          description: Radio callsign of the vessel.
          example: WDF5678
        name:
          type: string
          description: Name of the vessel.
          example: EVER GIVEN
        uscgVin:
          type: string
          description: United States Coast Guard Vessel Identification Number.
          example: '1234567'
        type:
          type: string
          description: Vessel type or category.
          example: Cargo
        grossTonnage:
          type: number
          description: Gross tonnage of the vessel.
          example: 220940
        deadweightTonnage:
          type: number
          description: Deadweight tonnage of the vessel.
          example: 199629
        ownerImoNumber:
          type: number
          description: IMO number of the vessel owner.
          example: 1234567
        buildDate:
          format: date-time
          type: string
          description: Date the vessel was built.
          example: '2018-09-25T00:00:00.000Z'
        buildYear:
          type: number
          description: Year the vessel was built.
          example: 2018
        buildMonth:
          type: number
          description: Month the vessel was built (1-12).
          example: 9
        flag:
          type: string
          description: Flag state of the vessel (country of registration).
          example: Panama
        status:
          type: string
          description: Current status of the vessel record.
          example: active
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the vessel record was created.
          example: '2024-01-15T08:30:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the vessel record was last updated.
          example: '2024-06-01T12:00:00.000Z'
      required:
        - id
        - mmsiNumber
        - createdAt
        - updatedAt
    SondeSite:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the sonde launch site.
          example: '155'
        flights:
          description: Flights launched from this site.
          type: array
          items:
            $ref: '#/components/schemas/SondeFlight'
        ident:
          type: string
          description: Identifier code for the launch site.
          example: '06260'
        name:
          type: string
          description: Name of the launch site.
          example: De Bilt
        description:
          type: string
          description: Description of the launch site.
          example: KNMI upper-air observation station
        latitude:
          type: number
          description: Latitude of the launch site (decimal degrees).
          example: 52.1015
        longitude:
          type: number
          description: Longitude of the launch site (decimal degrees).
          example: 5.1773
        altitude:
          type: number
          description: Altitude of the launch site in meters.
          example: 14
        types:
          type: string
          description: Sonde types launched from this site.
          example: RS41
        ascentRate:
          type: number
          description: Average ascent rate in meters per second.
          example: 5.2
        ascentSamples:
          type: number
          description: Number of samples used to compute the ascent rate.
          example: 1200
        ascentStdDev:
          type: number
          description: Standard deviation of the ascent rate.
          example: 0.4
        burstAltitude:
          type: number
          description: Average burst altitude in meters.
          example: 32000
        burstSamples:
          type: number
          description: Number of samples used to compute the burst altitude.
          example: 150
        burstStdDev:
          type: number
          description: Standard deviation of the burst altitude.
          example: 850
        descentRate:
          type: number
          description: Average descent rate in meters per second.
          example: 8.7
        descentSamples:
          type: number
          description: Number of samples used to compute the descent rate.
          example: 900
        descentStdDev:
          type: number
          description: Standard deviation of the descent rate.
          example: 1.1
        status:
          type: string
          description: Current status of the launch site record.
          example: active
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the launch site record was created.
          example: '2023-01-10T00:00:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the launch site record was last updated.
          example: '2024-06-01T00:00:00.000Z'
      required:
        - id
        - ident
        - latitude
        - longitude
        - createdAt
        - updatedAt
    SondeMessage:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the sonde telemetry message.
          example: '99001'
        station:
          description: The ground station that received this message.
          allOf:
            - $ref: '#/components/schemas/Station'
        sonde:
          description: The radiosonde that transmitted this message.
          allOf:
            - $ref: '#/components/schemas/Sonde'
        flight:
          description: The flight this message is associated with.
          allOf:
            - $ref: '#/components/schemas/SondeFlight'
        latitude:
          type: string
          description: Latitude reported in the message (decimal degrees).
          example: '52.1326'
        longitude:
          type: string
          description: Longitude reported in the message (decimal degrees).
          example: '5.2913'
        altitude:
          type: string
          description: Altitude reported in the message (meters).
          example: '24500'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the message record was created.
          example: '2024-06-01T07:42:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the message record was last updated.
          example: '2024-06-01T07:42:00.000Z'
      required:
        - id
        - latitude
        - longitude
        - altitude
        - createdAt
        - updatedAt
    SondeFlightPosition:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the flight position report.
          example: '770122'
        sonde:
          description: The radiosonde that reported this position.
          allOf:
            - $ref: '#/components/schemas/Sonde'
        flight:
          description: The flight this position report belongs to.
          allOf:
            - $ref: '#/components/schemas/SondeFlight'
        latitude:
          type: string
          description: Latitude of the reported position (decimal degrees).
          example: '52.1326'
        longitude:
          type: string
          description: Longitude of the reported position (decimal degrees).
          example: '5.2913'
        altitude:
          type: string
          description: Altitude of the reported position (meters).
          example: '24500'
        heading:
          type: string
          description: Heading of the sonde in degrees (0-359).
          example: '215'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the position report was created.
          example: '2024-06-01T07:42:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the position report was last updated.
          example: '2024-06-01T07:42:00.000Z'
      required:
        - id
        - latitude
        - longitude
        - altitude
        - createdAt
        - updatedAt
    SondeFlight:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the sonde flight.
          example: '8842'
        sonde:
          description: The radiosonde flown on this flight.
          allOf:
            - $ref: '#/components/schemas/Sonde'
        site:
          description: The launch site this flight was released from.
          allOf:
            - $ref: '#/components/schemas/SondeSite'
        messages:
          description: Telemetry messages received during this flight.
          type: array
          items:
            $ref: '#/components/schemas/SondeMessage'
        positions:
          description: Position reports recorded during this flight.
          type: array
          items:
            $ref: '#/components/schemas/SondeFlightPosition'
        lastHeardAt:
          format: date-time
          type: string
          description: Timestamp when the sonde was last heard on this flight.
          example: '2024-06-01T07:42:00.000Z'
        lastLatitude:
          type: string
          description: Latitude of the last reported position (decimal degrees).
          example: '52.1326'
        lastLongitude:
          type: string
          description: Longitude of the last reported position (decimal degrees).
          example: '5.2913'
        lastAltitude:
          type: number
          description: Altitude of the last reported position in meters.
          example: 24500
        startedAt:
          format: date-time
          type: string
          description: Timestamp when the flight (balloon launch) started.
          example: '2024-06-01T06:15:00.000Z'
        endedAt:
          format: date-time
          type: string
          description: Timestamp when the flight ended (landing or signal loss).
          example: '2024-06-01T08:05:00.000Z'
        status:
          type: string
          description: Current status of the flight.
          example: active
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the flight record was created.
          example: '2024-06-01T06:15:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the flight record was last updated.
          example: '2024-06-01T07:42:00.000Z'
      required:
        - id
        - lastHeardAt
        - lastLatitude
        - lastLongitude
        - status
        - createdAt
        - updatedAt
    Sonde:
      type: object
      properties:
        id:
          type: string
          description: Unique identifier for the radiosonde.
          example: '4321'
        serial:
          type: string
          description: Serial number of the radiosonde unit.
          example: S4830127
        type:
          type: string
          description: Type of radiosonde.
          example: RS41
        subtype:
          type: string
          description: Subtype or variant of the radiosonde.
          example: RS41-SGP
        manufacturer:
          type: string
          description: Manufacturer of the radiosonde.
          example: Vaisala
        status:
          type: string
          description: Current status of the radiosonde record.
          example: active
        flights:
          description: Flights flown by this radiosonde.
          type: array
          items:
            $ref: '#/components/schemas/SondeFlight'
        messages:
          description: Telemetry messages received from this radiosonde.
          type: array
          items:
            $ref: '#/components/schemas/SondeMessage'
        createdAt:
          format: date-time
          type: string
          description: Timestamp when the radiosonde record was created.
          example: '2024-06-01T05:00:00.000Z'
        updatedAt:
          format: date-time
          type: string
          description: Timestamp when the radiosonde record was last updated.
          example: '2024-06-01T06:30:00.000Z'
      required:
        - id
        - serial
        - createdAt
        - updatedAt
    UpdatePrivacyDto:
      type: object
      properties: {}
    CreateApiKeyDto:
      type: object
      properties: {}
    UpsertIntegrationDto:
      type: object
      properties: {}
    CreateNotificationDto:
      type: object
      properties: {}
    UpdateNotificationDto:
      type: object
      properties: {}
    UpdateStationAlertPreferencesDto:
      type: object
      properties: {}
    UpdateStationOutageSettingDto:
      type: object
      properties: {}
    CreateWebhookDto:
      type: object
      properties: {}
    UpdateWebhookDto:
      type: object
      properties: {}
    AcarsLabelDto:
      type: object
      properties:
        label:
          type: string
          example: H1
        count:
          type: number
          example: 18240
      required:
        - label
        - count
    AcarsSourceTypeDto:
      type: object
      properties:
        sourceType:
          type: string
          example: acars
        count:
          type: number
          example: 42010
      required:
        - sourceType
        - count
    AcarsMessageWindowDto:
      type: object
      properties:
        total:
          type: number
          example: 52310
          description: Total messages in the window
        labels:
          type: array
          items:
            $ref: '#/components/schemas/AcarsLabelDto'
        sourceTypes:
          type: array
          items:
            $ref: '#/components/schemas/AcarsSourceTypeDto'
      required:
        - total
        - labels
        - sourceTypes
    AcarsMessagesStatsDto:
      type: object
      properties:
        lastHour:
          $ref: '#/components/schemas/AcarsMessageWindowDto'
        last24Hours:
          $ref: '#/components/schemas/AcarsMessageWindowDto'
      required:
        - lastHour
        - last24Hours
    AcarsStatsDto:
      type: object
      properties:
        messages:
          $ref: '#/components/schemas/AcarsMessagesStatsDto'
      required:
        - messages
    AcarsStatsResponseDto:
      type: object
      properties:
        stats:
          $ref: '#/components/schemas/AcarsStatsDto'
      required:
        - stats
    StationsStatsDto:
      type: object
      properties:
        total:
          type: number
          example: 1240
          description: Total number of stations
        byStatus:
          type: object
          additionalProperties: true
          description: >-
            Dynamic per-status breakdown of stations keyed by status (e.g. "active", "inactive",
            "pending-reception", "secret"). Each value has a "total" and an optional
            type/source_type breakdown.
          example:
            active:
              total: 980
              ground:
                acars: 410
                vdl: 260
                hfdl: 90
            inactive:
              total: 180
            pending-reception:
              total: 60
            secret:
              total: 20
      required:
        - total
        - byStatus
    CountWrapperDto:
      type: object
      properties:
        total:
          type: number
          example: 0
      required:
        - total
    FlightCountsDto:
      type: object
      properties:
        active:
          type: number
          example: 320
          description: Currently active flights
        total:
          type: number
          example: 1850320
          description: Total flights recorded
      required:
        - active
        - total
    AirframesStatsDto:
      type: object
      properties:
        airframes:
          $ref: '#/components/schemas/CountWrapperDto'
        flights:
          $ref: '#/components/schemas/FlightCountsDto'
      required:
        - airframes
        - flights
    VoyageCountsDto:
      type: object
      properties:
        active:
          type: number
          example: 540
          description: Currently active voyages
        total:
          type: number
          example: 92010
          description: Total voyages recorded
      required:
        - active
        - total
    MarineStatsDto:
      type: object
      properties:
        voyages:
          $ref: '#/components/schemas/VoyageCountsDto'
      required:
        - voyages
    SondeFlightCountsDto:
      type: object
      properties:
        active:
          type: number
          example: 75
          description: Currently active sonde flights
        total:
          type: number
          example: 41200
          description: Total sonde flights recorded
      required:
        - active
        - total
    SondeStatsDto:
      type: object
      properties:
        flights:
          $ref: '#/components/schemas/SondeFlightCountsDto'
      required:
        - flights
    PlatformStatsDto:
      type: object
      properties:
        stations:
          $ref: '#/components/schemas/StationsStatsDto'
        airframes:
          $ref: '#/components/schemas/AirframesStatsDto'
        marine:
          $ref: '#/components/schemas/MarineStatsDto'
        sonde:
          $ref: '#/components/schemas/SondeStatsDto'
      required:
        - stations
        - airframes
        - marine
        - sonde
    PlatformStatsResponseDto:
      type: object
      properties:
        stats:
          $ref: '#/components/schemas/PlatformStatsDto'
      required:
        - stats
    CreateCheckoutDto:
      type: object
      properties: {}
    CreateSponsorCheckoutDto:
      type: object
      properties: {}
    CancelSponsorDto:
      type: object
      properties: {}
    DecodeCoverageSourceTypeDto:
      type: object
      properties:
        source_type:
          type: string
          example: acars
        messages:
          type: number
          example: 1250340
        decodings:
          type: number
          example: 980210
        positions:
          type: number
          example: 145200
        position_pct:
          type: number
          example: 11.6
          description: Percentage of messages with a position
      required:
        - source_type
        - messages
        - decodings
        - positions
        - position_pct
    DecodeCoverageDecoderDto:
      type: object
      properties:
        decoder_name:
          type: string
          example: libacars
        decoder_type:
          type: string
          example: acars
        count:
          type: number
          example: 532010
      required:
        - decoder_name
        - decoder_type
        - count
    DecodeCoverageResponseDto:
      type: object
      properties:
        total_messages:
          type: number
          example: 2500000
        total_decodings:
          type: number
          example: 1800000
        messages_with_decodings:
          type: number
          example: 1650000
        coverage_pct:
          type: number
          example: 66
          description: Percentage of messages with at least one decoding
        positions_total:
          type: number
          example: 210400
        position_rate_pct:
          type: number
          example: 8.4
          description: Percentage of messages that carry a position
        decoder_types:
          type: number
          example: 6
        by_source_type:
          type: array
          items:
            $ref: '#/components/schemas/DecodeCoverageSourceTypeDto'
        by_decoder:
          type: array
          items:
            $ref: '#/components/schemas/DecodeCoverageDecoderDto'
      required:
        - total_messages
        - total_decodings
        - messages_with_decodings
        - coverage_pct
        - positions_total
        - position_rate_pct
        - decoder_types
        - by_source_type
        - by_decoder
    DecodeLabelEntryDto:
      type: object
      properties:
        label:
          type: string
          example: H1
        total:
          type: number
          example: 84200
        decoded:
          type: number
          example: 61300
        undecoded:
          type: number
          example: 22900
        coverage_pct:
          type: number
          example: 72.8
        decoders_used:
          example:
            - libacars
            - acarsdec
          type: array
          items:
            type: string
      required:
        - label
        - total
        - decoded
        - undecoded
        - coverage_pct
        - decoders_used
    DecodeLabelCoverageResponseDto:
      type: object
      properties:
        labels:
          type: array
          items:
            $ref: '#/components/schemas/DecodeLabelEntryDto'
      required:
        - labels
    DecodePositionEntryDto:
      type: object
      properties:
        message_id:
          type: number
          example: 1048576
        lat:
          type: number
          example: 37.6189
        lon:
          type: number
          example: -122.375
        alt:
          type: number
          example: 35000
          nullable: true
        source_type:
          type: string
          example: acars
        tail:
          type: string
          example: N12345
          nullable: true
        flight:
          type: string
          example: UAL123
          nullable: true
        decoder:
          type: string
          example: libacars
        timestamp:
          type: string
          example: '2026-06-05T12:34:56.000Z'
      required:
        - message_id
        - lat
        - lon
        - alt
        - source_type
        - tail
        - flight
        - decoder
        - timestamp
    DecodePositionsResponseDto:
      type: object
      properties:
        positions:
          type: array
          items:
            $ref: '#/components/schemas/DecodePositionEntryDto'
      required:
        - positions
    FlagStationDto:
      type: object
      properties: {}
    StationRankEntryDto:
      type: object
      properties:
        rank:
          type: number
          example: 1
        stationId:
          type: number
          example: 1024
        stationIdent:
          type: string
          example: KSFO-1
        countryCode:
          type: string
          example: US
        flagEmoji:
          type: string
          example: 🇺🇸
        sourceType:
          type: string
          example: acars
        userId:
          type: string
          example: a1b2c3d4-0000-0000-0000-000000000001
          nullable: true
        username:
          type: string
          example: kevin
          nullable: true
        count:
          type: number
          example: 184230
          description: >-
            Primary ranking value for this entry (message count, distinct count, or composite score
            depending on category).
        messagesCount:
          type: number
          example: 184230
        entitiesCount:
          type: number
          example: 4210
        tracksCount:
          type: number
          example: 3120
        maxDistanceNm:
          type: number
          example: 312.4
        activeStreakDays:
          type: number
          example: 42
        uptimePercent:
          type: number
          example: 98
        coverageAreaSqNm:
          type: number
          example: 1250.5
        uniqueFrequencies:
          type: number
          example: 12
        peakHour:
          type: number
          example: 14
      required:
        - rank
        - stationId
        - stationIdent
        - countryCode
        - flagEmoji
        - sourceType
        - userId
        - username
        - count
    UserRankEntryDto:
      type: object
      properties:
        rank:
          type: number
          example: 1
        userId:
          type: string
          example: a1b2c3d4-0000-0000-0000-000000000001
        username:
          type: string
          example: kevin
        gravatarUrl:
          type: string
          example: https://www.gravatar.com/avatar/abcdef0123456789?s=100
        stationCount:
          type: number
          example: 3
        count:
          type: number
          example: 412300
          description: >-
            Primary ranking value for this user (summed count or composite score depending on
            category).
        messagesCount:
          type: number
          example: 412300
        entitiesCount:
          type: number
          example: 8210
        tracksCount:
          type: number
          example: 6120
        maxDistanceNm:
          type: number
          example: 312.4
        bestStreakDays:
          type: number
          example: 42
        avgUptimePercent:
          type: number
          example: 96
      required:
        - rank
        - userId
        - username
        - gravatarUrl
        - stationCount
        - count
    LeaderboardMetaDto:
      type: object
      properties:
        updatedAt:
          type: string
          example: '2026-06-05T12:00:00.000Z'
        computeDurationMs:
          type: number
          example: 1842
          description: Computation duration in milliseconds
        aircraftStationCount:
          type: number
          example: 980
        marineStationCount:
          type: number
          example: 240
        totalStationCount:
          type: number
          example: 1220
      required:
        - updatedAt
        - computeDurationMs
        - aircraftStationCount
        - marineStationCount
        - totalStationCount
    LeaderboardResponseDto:
      type: object
      properties:
        updatedAt:
          type: string
          example: '2026-06-05T12:00:00.000Z'
        domain:
          type: string
          example: aircraft
          enum:
            - aircraft
            - marine
            - combined
        view:
          type: string
          example: station
          enum:
            - station
            - user
        category:
          type: string
          example: messages
          description: >-
            Ranking category. Valid values depend on the domain (e.g. messages, airframes, flights,
            vessels, voyages, entities, tracks, composite).
        timeframe:
          type: string
          example: 30d
          enum:
            - 24h
            - 30d
            - all-time
        entries:
          type: array
          description: >-
            Ranked entries. Station views return StationRankEntryDto items; user views return
            UserRankEntryDto items.
          items:
            oneOf:
              - $ref: '#/components/schemas/StationRankEntryDto'
              - $ref: '#/components/schemas/UserRankEntryDto'
      required:
        - updatedAt
        - domain
        - view
        - category
        - timeframe
        - entries
    UpdateDmNotificationPreferenceDto:
      type: object
      properties: {}
    FrequencyUsageSummaryDto:
      type: object
      properties:
        period:
          type: string
          example: day
          enum:
            - day
            - week
            - month
            - year
        periodStart:
          type: string
          example: '2026-06-05T00:00:00.000Z'
        periodEnd:
          type: string
          example: '2026-06-06T00:00:00.000Z'
        calculatedAt:
          type: string
          example: '2026-06-05T12:00:00.000Z'
        messageCount:
          type: number
          example: 1850320
        stationFrequencyCount:
          type: number
          example: 4210
        frequencyCountryCount:
          type: number
          example: 920
        protocolCount:
          type: number
          example: 5
        countryCount:
          type: number
          example: 84
      required:
        - period
        - periodStart
        - periodEnd
        - calculatedAt
        - messageCount
        - stationFrequencyCount
        - frequencyCountryCount
        - protocolCount
        - countryCount
    FrequencyUsageProtocolFilterDto:
      type: object
      properties:
        protocol:
          type: string
          example: acars
        messageCount:
          type: number
          example: 920310
      required:
        - protocol
        - messageCount
    FrequencyUsageCountryFilterDto:
      type: object
      properties:
        countryCode:
          type: string
          example: US
        countryName:
          type: string
          example: United States
        messageCount:
          type: number
          example: 740120
      required:
        - countryCode
        - countryName
        - messageCount
    FrequencyUsageFiltersDto:
      type: object
      properties:
        protocols:
          type: array
          items:
            $ref: '#/components/schemas/FrequencyUsageProtocolFilterDto'
        countries:
          type: array
          items:
            $ref: '#/components/schemas/FrequencyUsageCountryFilterDto'
      required:
        - protocols
        - countries
    FrequencyUsageRowDto:
      type: object
      properties:
        period:
          type: string
          example: day
        periodStart:
          type: string
          example: '2026-06-05T00:00:00.000Z'
        periodEnd:
          type: string
          example: '2026-06-06T00:00:00.000Z'
        calculatedAt:
          type: string
          example: '2026-06-05T12:00:00.000Z'
        protocol:
          type: string
          example: acars
        countryCode:
          type: string
          example: US
        countryName:
          type: string
          example: United States
        frequency:
          type: string
          example: '131.550'
        messageCount:
          type: number
          example: 18240
        stationCount:
          type: number
          example: 42
      required:
        - period
        - periodStart
        - periodEnd
        - calculatedAt
        - protocol
        - countryCode
        - countryName
        - frequency
        - messageCount
        - stationCount
    FrequencyUsageResponseDto:
      type: object
      properties:
        period:
          type: string
          example: day
          enum:
            - day
            - week
            - month
            - year
        periodStart:
          type: string
          example: '2026-06-05T00:00:00.000Z'
          nullable: true
        periodEnd:
          type: string
          example: '2026-06-06T00:00:00.000Z'
          nullable: true
        calculatedAt:
          type: string
          example: '2026-06-05T12:00:00.000Z'
          nullable: true
        summary:
          type: array
          items:
            $ref: '#/components/schemas/FrequencyUsageSummaryDto'
        filters:
          $ref: '#/components/schemas/FrequencyUsageFiltersDto'
        rows:
          type: array
          items:
            $ref: '#/components/schemas/FrequencyUsageRowDto'
      required:
        - period
        - periodStart
        - periodEnd
        - calculatedAt
        - summary
        - filters
        - rows
    ApiError:
      type: object
      properties:
        statusCode:
          type: integer
          example: 429
        message:
          description: Error message, or an array of validation messages.
          oneOf:
            - type: string
            - type: array
              items:
                type: string
          example: Too Many Requests
        error:
          type: string
          example: Too Many Requests
        timestamp:
          type: string
          format: date-time
externalDocs:
  description: Airframes Docs
  url: https://docs.airframes.io/api
