openapi: 3.0.0
info:
  title: AURA Engine API
  description: This is the AURA Engine API.
  contact:
    email: david.trattnig@subsquare.at
  license:
    name: AGPL 3.0
    url: https://www.gnu.org/licenses/agpl-3.0.en.html
  version: 1.0.0
externalDocs:
  description: Find more info here
  url: https://gitlab.servus.at/aura/engine-api
servers:
- url: "{protocol}://{api-host}:{port}/api/{version}"
  description: Engine API
  variables:
    protocol:
      default: http
      enum:
      - http
      - https
    api-host:
      description: Hostname or IP for API Host
      default: localhost
    port:
      default: "8008"
    version:
      default: v1
- url: https://virtserver.swaggerhub.com/AURA-Engine/engine-api/1.0.0
  description: SwaggerHub API Auto Mocking
tags:
- name: public
  description: Operations available to the public
- name: internal
  description: Secured calls only
paths:
  /trackservice:
    get:
      tags:
      - public
      summary: List recent tracks in the play-log
      description: |
        Lists the track-service entries for a given page.
      operationId: list_tracks
      parameters:
      - name: fromDate
        in: query
        description: Get entries after this timestamp
        required: false
        style: form
        explode: true
        schema:
          type: string
          format: date-time
        example: 2020-08-29T09:12:33.001Z
      - name: toDate
        in: query
        description: Get entries before this timestamp
        required: false
        style: form
        explode: true
        schema:
          type: string
          format: date-time
        example: 2020-11-29T09:12:55.001Z
      - name: page
        in: query
        description: The number of items to skip before starting to collect the result
          set
        required: false
        style: form
        explode: true
        schema:
          type: integer
      - name: limit
        in: query
        description: The numbers of items to return per page
        required: false
        style: form
        explode: true
        schema:
          maximum: 50
          minimum: 1
          type: integer
          default: 20
      responses:
        "200":
          description: search results matching criteria
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Track'
                x-content-type: application/json
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.public_controller
  /trackservice/current:
    get:
      tags:
      - public
      summary: Get current track
      description: |
        Retrieves the currently playing track.
      operationId: current_track
      responses:
        "200":
          description: Track currently playing
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Track'
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.public_controller
  /clock:
    get:
      tags:
      - internal
      summary: Get all information to display the studio clock
      description: |
        Retrieves the currently playing timeslot, its playlist and entries plus the next timeslot for being used by the studio clock.
      operationId: clock_info
      responses:
        "200":
          description: "Show, Timeslot and Playlist info for the Studio Clock"
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ClockInfo'
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
    put:
      tags:
      - internal
      summary: Set current studio clock information such as timeslot info and track-list
        for engine 1 or 2 within the Engine API database.
      description: |
        Set current studio clock information (source, timeslot and planned track-list) and the next timeslot of the given play-out source (engine1, engine2). Please note, the `currentTrack` and `currentPlaylogs` information is ignored in the PUT request. It's only dynamically populated in the GET request by reading the most recent playlog. To store current track information use `/playlog` instead. Also note, similar to the `PlayLog` storage endpoint, this information is only stored to the database if a) it is a main node or b) if it's a sync node, and the `engineSource` is the currently active engine.
      operationId: set_clock_info
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ClockInfo'
        required: true
      responses:
        "204":
          description: status updated
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
  /playlog:
    get:
      tags:
      - internal
      summary: List tracks in the play-log since the given timestamp
      description: |
        Get paginated playlog entries for since the given timestamp.
      operationId: list_playlog
      parameters:
      - name: fromDate
        in: query
        description: Get entries after this timestamp
        required: false
        style: form
        explode: true
        schema:
          type: string
          format: date-time
        example: 2020-08-29T09:12:33.001Z
      - name: toDate
        in: query
        description: Get entries before this timestamp
        required: false
        style: form
        explode: true
        schema:
          type: string
          format: date-time
        example: 2020-11-29T09:12:55.001Z
      - name: page
        in: query
        description: The number of items to skip before starting to collect the result
          set
        required: false
        style: form
        explode: true
        schema:
          type: integer
      - name: limit
        in: query
        description: The numbers of items to return per page
        required: false
        style: form
        explode: true
        schema:
          maximum: 200
          minimum: 1
          type: integer
          default: 50
      - name: skipSynced
        in: query
        description: If true only returns items which are in unsynced state on the
          main node
        required: false
        style: form
        explode: true
        schema:
          type: boolean
      responses:
        "200":
          description: search results matching criteria
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/PlayLog'
                x-content-type: application/json
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
    post:
      tags:
      - internal
      summary: Adds an entry to the playlog
      description: |
        Stores the passed playlog entry in the local database. Also note, similar to the `ClockInfo` storage endpoint, this information is only stored to the database if a) it is a main node or b) if it's a sync node, and the `logSource` is the currently active engine.
      operationId: add_playlog
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PlayLog'
        required: true
      responses:
        "204":
          description: Successfully created a new playlog
        "400":
          description: Invalid request
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/inline_response_400'
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
  /playlog/report/{year_month}:
    get:
      tags:
      - internal
      summary: Report for one month
      description: |
        Returns a report for the given month
      operationId: get_report
      parameters:
      - name: year_month
        in: path
        description: Month to create the report for in the format "yyyy_mm"
        required: true
        style: simple
        explode: false
        schema:
          type: string
      responses:
        "200":
          description: report matching criteria
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/PlayLog'
                x-content-type: application/json
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
  /source/active:
    get:
      tags:
      - internal
      summary: "Get active play-out source (engine1, engine2)"
      description: |
        Retrieves the status entry of the currently active source (engine 1, 2 or other source)
      operationId: get_active_source
      responses:
        "200":
          description: source number
          content:
            application/json:
              schema:
                type: integer
                x-content-type: application/json
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
  /source/active/{number}:
    put:
      tags:
      - internal
      summary: "Set active play-out source (engine1, engine2)"
      description: |
        Activates one engine and deactivates the other
      operationId: set_active_source
      parameters:
      - name: number
        in: path
        description: Number of the engine
        required: true
        style: simple
        explode: false
        schema:
          maximum: 2
          minimum: 1
          type: integer
      responses:
        "204":
          description: status updated
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
  /source/health/{number}:
    get:
      tags:
      - internal
      summary: Get most recent health info
      description: |
        Retrieves the most recent health info of the requested engine
      operationId: get_source_health
      parameters:
      - name: number
        in: path
        description: Number of the engine
        required: true
        style: simple
        explode: false
        schema:
          maximum: 2
          minimum: 1
          type: integer
      responses:
        "200":
          description: report matching criteria
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/HealthLog'
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
    post:
      tags:
      - internal
      summary: Log health info
      description: |
        Logs another health entry for the given engine
      operationId: log_source_health
      parameters:
      - name: number
        in: path
        description: Number of the engine
        required: true
        style: simple
        explode: false
        schema:
          minimum: 1
          type: integer
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/HealthLog'
        required: true
      responses:
        "204":
          description: health info logged
        "400":
          description: bad input parameter
      x-openapi-router-controller: aura_engine_api.rest.controllers.internal_controller
components:
  schemas:
    Track:
      required:
      - trackStart
      type: object
      properties:
        trackStart:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        trackArtist:
          type: string
          example: Kyuss
        trackAlbum:
          type: string
          example: '... And the Circus Leaves Town'
        trackTitle:
          type: string
          example: El Rodeo
        trackDuration:
          type: integer
          example: 303
        trackType:
          type: integer
          description: "Indicates the type: \"0\" = filesystem, \"1\" = stream, \"\
            2\" = live or line in"
          example: 2
        trackNum:
          type: integer
          example: 11
        playlistId:
          type: integer
          example: 38
        timeslotId:
          type: integer
          example: 23
        showId:
          type: integer
          example: 42
        showName:
          type: string
          example: Electronic Music from Brazil
      description: Holds all information required to display a public Track Service
        entry. This schema is a sub-set of the `PlayLog` schema.
      example:
        playlistId: 38
        trackNum: 11
        showId: 42
        showName: Electronic Music from Brazil
        trackType: 2
        timeslotId: 23
        trackArtist: Kyuss
        trackAlbum: '... And the Circus Leaves Town'
        trackDuration: 303
        trackStart: 2020-08-29T09:12:33.001Z
        trackTitle: El Rodeo
    PlayLog:
      required:
      - trackStart
      type: object
      properties:
        trackStart:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        trackArtist:
          type: string
          example: Amon Tobin
        trackAlbum:
          type: string
          example: Bricolage
        trackTitle:
          type: string
          example: Chomp Samba
        trackDuration:
          type: integer
          example: 808
        trackType:
          type: integer
          description: "Indicates the type: \"0\" = filesystem, \"1\" = stream, \"\
            2\" = live or line in"
          example: 2
        trackNum:
          type: integer
          example: 11
        playlistId:
          type: integer
          example: 38
        timeslotId:
          type: integer
          example: 23
        showId:
          type: integer
          example: 42
        showName:
          type: string
          example: Electronic Music from Brazil
        logSource:
          type: integer
          description: From which engine the entry has been logged from e.g. "1" for
            Engine 1 or "2" for Engine 2
          example: 1
        customJson:
          type: string
          description: A stringified JSON Object allowing the future extension of
            the API with custom fields.
          example: "{ \"custom\": \"Stringified JSON Object\" }"
        isSynced:
          type: boolean
          description: For Engine API internal use only - On a main node such as Engine
            1 or 2 this flag indicates if the playlog has been actively synced to
            the sync node. On the sync node in contrast this flag indicates if the
            playlog has been passively synced from one of the main nodes.
          example: true
      description: Holds all information available to the currently playing track.
        This schema is a super-set of the `Track` schema.
      example:
        playlistId: 38
        trackNum: 11
        isSynced: true
        showName: Electronic Music from Brazil
        trackType: 2
        logSource: 1
        trackArtist: Amon Tobin
        customJson: "{ \"custom\": \"Stringified JSON Object\" }"
        trackStart: 2020-08-29T09:12:33.001Z
        trackTitle: Chomp Samba
        showId: 42
        timeslotId: 23
        trackAlbum: Bricolage
        trackDuration: 808
    HealthLog:
      required:
      - details
      - isHealthy
      - logTime
      type: object
      properties:
        logTime:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        isHealthy:
          type: boolean
          example: true
        details:
          type: string
          description: Stringified JSON Object
          example: "{ \"health_info\": \"{\\\"engine\\\": {\\\"version\\\": \\\"1.0.0-alpha1\\\
            \", \\\"status\\\": \\\"OK\\\"}, \\\"lqs\\\": {\\\"version\\\": {\\\"\
            core\\\": \\\"1.0.0-alpha1\\\", \\\"liquidsoap\\\": \\\"2.1.0\\\"}, \\\
            \"outputs\\\": {\\\"stream\\\": [], \\\"line\\\": [\\\"out_line_0\\\"\
            ]}, \\\"mixer\\\": {\\\"in_filesystem_0\\\": \\\"ready=false selected=false\
            \ single=false volume=0% remaining=0.\\\", \\\"in_filesystem_1\\\": \\\
            \"ready=false selected=false single=false volume=0% remaining=0.\\\",\
            \ \\\"in_http_0\\\": \\\"ready=true selected=true single=false volume=0%\
            \ remaining=inf\\\", \\\"in_http_1\\\": \\\"ready=false selected=false\
            \ single=false volume=0% remaining=inf\\\"}, \\\"status\\\": {\\\"uptime\\\
            \": \\\"0d 00h 50m 12s\\\", \\\"is_fallback\\\": false}, \\\"available\\\
            \": true}, \\\"api\\\": {\\\"steering\\\": {\\\"url\\\": \\\"http://aura.local/steering/api/v1/\\\
            \", \\\"available\\\": true}, \\\"tank\\\": {\\\"url\\\": \\\"http://aura.local/tank/healthz\\\
            \", \\\"available\\\": true, \\\"status\\\": {\\\"auth\\\": \\\"OK\\\"\
            , \\\"store\\\": \\\"OK\\\", \\\"importer\\\": \\\"OK\\\"}}, \\\"engine\\\
            \": {\\\"url\\\": \\\"http://localhost:8008/api/v1/ui/\\\", \\\"available\\\
            \": true}}, \\\"audio_source\\\": {\\\"path\\\": \\\"/opt/aura/audio/source\\\
            \", \\\"exists\\\": true, \\\"has_content\\\": true}}\", \"is_healthy\"\
            : true, \"is_synced\": false, \"log_source\": 1, \"log_time\": \"2022-08-04T19:47:16.827407\"\
            \ }"
      description: "Holds unspecified and extendable health information for both,\
        \ valid and invalid states of the playout engine(s). The data is stored in\
        \ form of stringified JSON."
      example:
        details: "{ \"health_info\": \"{\\\"engine\\\": {\\\"version\\\": \\\"1.0.0-alpha1\\\
          \", \\\"status\\\": \\\"OK\\\"}, \\\"lqs\\\": {\\\"version\\\": {\\\"core\\\
          \": \\\"1.0.0-alpha1\\\", \\\"liquidsoap\\\": \\\"2.1.0\\\"}, \\\"outputs\\\
          \": {\\\"stream\\\": [], \\\"line\\\": [\\\"out_line_0\\\"]}, \\\"mixer\\\
          \": {\\\"in_filesystem_0\\\": \\\"ready=false selected=false single=false\
          \ volume=0% remaining=0.\\\", \\\"in_filesystem_1\\\": \\\"ready=false selected=false\
          \ single=false volume=0% remaining=0.\\\", \\\"in_http_0\\\": \\\"ready=true\
          \ selected=true single=false volume=0% remaining=inf\\\", \\\"in_http_1\\\
          \": \\\"ready=false selected=false single=false volume=0% remaining=inf\\\
          \"}, \\\"status\\\": {\\\"uptime\\\": \\\"0d 00h 50m 12s\\\", \\\"is_fallback\\\
          \": false}, \\\"available\\\": true}, \\\"api\\\": {\\\"steering\\\": {\\\
          \"url\\\": \\\"http://aura.local/steering/api/v1/\\\", \\\"available\\\"\
          : true}, \\\"tank\\\": {\\\"url\\\": \\\"http://aura.local/tank/healthz\\\
          \", \\\"available\\\": true, \\\"status\\\": {\\\"auth\\\": \\\"OK\\\",\
          \ \\\"store\\\": \\\"OK\\\", \\\"importer\\\": \\\"OK\\\"}}, \\\"engine\\\
          \": {\\\"url\\\": \\\"http://localhost:8008/api/v1/ui/\\\", \\\"available\\\
          \": true}}, \\\"audio_source\\\": {\\\"path\\\": \\\"/opt/aura/audio/source\\\
          \", \\\"exists\\\": true, \\\"has_content\\\": true}}\", \"is_healthy\"\
          : true, \"is_synced\": false, \"log_source\": 1, \"log_time\": \"2022-08-04T19:47:16.827407\"\
          \ }"
        logTime: 2020-08-29T09:12:33.001Z
        isHealthy: true
    ClockInfo:
      type: object
      properties:
        engineSource:
          type: integer
          example: 1
        currentTrack:
          $ref: '#/components/schemas/PlayLog'
        currentPlaylogs:
          type: array
          nullable: true
          items:
            $ref: '#/components/schemas/PlayLog'
        plannedPlaylist:
          $ref: '#/components/schemas/Playlist'
        currentTimeslot:
          $ref: '#/components/schemas/Timeslot'
        upcomingTimeslots:
          type: array
          nullable: true
          items:
            $ref: '#/components/schemas/Timeslot'
      description: "Holds the most recent data required to display the studio clock.\
        \ The field `engineSource` will most likely be the same value as `currentTrack.logSource`.\
        \ This value represents which engine the record has been logged from. If it\
        \ is not equal for both fields, it most likely indicates an error or an engine\
        \ 1 to engine 2 transition process. Another reason is you are using the API\
        \ in some quite futuristic environment, where e.g. an external audio backup\
        \ player is able to log its meta data of what it is playing to the Engine\
        \ API, while the actual `ClockInfo` was logged from an engine instance instead."
      example:
        plannedPlaylist:
          playlistId: 38
          entries:
          - trackNum: 7
            trackType: 2
            trackArtist: Amon Tobin
            trackAlbum: Bricolage
            trackDuration: 808
            trackStart: 2020-08-29T09:12:33.001Z
            trackTitle: Chomp Samba
          - trackNum: 7
            trackType: 2
            trackArtist: Amon Tobin
            trackAlbum: Bricolage
            trackDuration: 808
            trackStart: 2020-08-29T09:12:33.001Z
            trackTitle: Chomp Samba
        currentTrack:
          playlistId: 38
          trackNum: 11
          isSynced: true
          showName: Electronic Music from Brazil
          trackType: 2
          logSource: 1
          trackArtist: Amon Tobin
          customJson: "{ \"custom\": \"Stringified JSON Object\" }"
          trackStart: 2020-08-29T09:12:33.001Z
          trackTitle: Chomp Samba
          showId: 42
          timeslotId: 23
          trackAlbum: Bricolage
          trackDuration: 808
        currentPlaylogs:
        - null
        - null
        engineSource: 1
        currentTimeslot:
          playlistId: 38
          showName: Electronic Music from Brazil
          showId: 42
          timeslotEnd: 2020-08-29T09:12:33.001Z
          timeslotId: 23
          timeslotStart: 2020-08-29T09:12:33.001Z
          playlistType: 0
        upcomingTimeslots:
        - null
        - null
    Timeslot:
      required:
      - showName
      type: object
      properties:
        showName:
          type: string
          example: Electronic Music from Brazil
        showId:
          type: integer
          example: 42
        timeslotId:
          type: integer
          example: 23
        timeslotStart:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        timeslotEnd:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        playlistId:
          type: integer
          nullable: true
          example: 38
        playlistType:
          type: integer
          description: "Indicates on which scheduling level the playlist was assigned\
            \ to the timeslot (-1=fallback, 0=timeslot, 1=schedule, 2=show, 3=station)"
          example: 0
      description: Holds data describing some timeslot. Used by `ClockInfo` for the
        studio clock.
      example:
        playlistId: 38
        showName: Electronic Music from Brazil
        showId: 42
        timeslotEnd: 2020-08-29T09:12:33.001Z
        timeslotId: 23
        timeslotStart: 2020-08-29T09:12:33.001Z
        playlistType: 0
    Playlist:
      required:
      - entries
      type: object
      properties:
        playlistId:
          type: integer
          nullable: true
          example: 38
        entries:
          type: array
          items:
            $ref: '#/components/schemas/PlaylistEntry'
      description: Holds data describing some playlist. Used by `ClockInfo` for the
        studio clock.
      example:
        playlistId: 38
        entries:
        - trackNum: 7
          trackType: 2
          trackArtist: Amon Tobin
          trackAlbum: Bricolage
          trackDuration: 808
          trackStart: 2020-08-29T09:12:33.001Z
          trackTitle: Chomp Samba
        - trackNum: 7
          trackType: 2
          trackArtist: Amon Tobin
          trackAlbum: Bricolage
          trackDuration: 808
          trackStart: 2020-08-29T09:12:33.001Z
          trackTitle: Chomp Samba
    PlaylistEntry:
      required:
      - trackStart
      type: object
      properties:
        trackStart:
          type: string
          format: date-time
          example: 2020-08-29T09:12:33.001Z
        trackArtist:
          type: string
          example: Amon Tobin
        trackAlbum:
          type: string
          example: Bricolage
        trackTitle:
          type: string
          example: Chomp Samba
        trackDuration:
          type: integer
          example: 808
        trackType:
          type: integer
          example: 2
        trackNum:
          type: integer
          example: 7
      description: "Holds data describing some playlist entry. Used by `Playlist`,\
        \ indirectly by the studio clock data."
      example:
        trackNum: 7
        trackType: 2
        trackArtist: Amon Tobin
        trackAlbum: Bricolage
        trackDuration: 808
        trackStart: 2020-08-29T09:12:33.001Z
        trackTitle: Chomp Samba
    inline_response_400:
      type: object
      properties:
        message:
          type: string

