{"openapi":"3.1.0","info":{"title":"Screenly (BYOK) API","version":"0.1.0","description":"Screenly (BYOK) lets an AI assistant read your own Screenly data through the Screenly API with a key you supply (Screenly API token). Read-only: 10 tools (list_screens, list_screen_statuses, list_screen_reports, list_assets, list_asset_groups, list_playlists, list_playlist_items, list_labels, list_screen_labels, list_playlist_labels). The BYOK key travels with each request, is used for that one...\n\nEvery operation is read-only or compute-only. The same tools are available over MCP (streamable HTTP) at https://byok-screenly.connectorbay.com/mcp.","contact":{"name":"Unify Dynamics LLC","email":"agent@connectorbay.com","url":"https://connectorbay.com/byok-screenly/docs"},"termsOfService":"https://connectorbay.com/byok-screenly/terms"},"servers":[{"url":"https://byok-screenly.connectorbay.com"}],"externalDocs":{"url":"https://connectorbay.com/byok-screenly/docs"},"security":[{"upstreamKey":[]}],"components":{"securitySchemes":{"bearer":{"type":"http","scheme":"bearer","description":"Optional. A Pro API key raises rate limits; no credentials are required."},"upstreamKey":{"type":"apiKey","in":"header","name":"X-Upstream-Key","description":"Your own key for the service this connector wraps (bring your own key). Used for that one call only; never stored, logged or cached."}},"schemas":{"Error":{"type":"object","properties":{"ok":{"const":false},"error":{"type":"object"}}}}},"paths":{"/v1/tools/list_screens":{"post":{"operationId":"list_screens","summary":"List the signage screens (players) in the account with name, location text, time zone, type and whether they are enabled","description":"List the signage screens (players) in the account with name, location text, time zone, type and whether they are enabled. Use for \"Which Screenly screens do I have and where are they\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"name":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on screen name in PostgREST syntax, for example 'ilike.*lobby*'.","title":"Name"},"is_enabled":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on enabled state in PostgREST syntax, for example 'eq.true'.","title":"Is Enabled"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'name.asc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_screensArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_screen_statuses":{"post":{"operationId":"list_screen_statuses","summary":"List each screen's online state and whether its playlist is in sync with the web console. Use for \"Which of my Screenly ","description":"List each screen's online state and whether its playlist is in sync with the web console. Use for \"Which of my Screenly screens are offline\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"is_online":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on online state in PostgREST syntax, for example 'eq.false'.","title":"Is Online"},"in_sync":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on sync state in PostgREST syntax, for example 'eq.false'.","title":"In Sync"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_screen_statusesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_screen_reports":{"post":{"operationId":"list_screen_reports","summary":"List the latest health report per screen: player software and hardware version, uptime in seconds and last report time. ","description":"List the latest health report per screen: player software and hardware version, uptime in seconds and last report time. Use for \"What software version and uptime do my Screenly players report\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"screen_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on screen id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Screen Id"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'updated_at.desc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_screen_reportsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_assets":{"post":{"operationId":"list_assets","summary":"List content assets (images, videos, web pages) with title, type, processing status, size and dimensions. Use for \"Which","description":"List content assets (images, videos, web pages) with title, type, processing status, size and dimensions. Use for \"Which video assets are in my Screenly library\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"type":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on asset type in PostgREST syntax, for example 'eq.video'.","title":"Type"},"title":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on title in PostgREST syntax, for example 'ilike.*menu*'.","title":"Title"},"asset_group_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on asset group id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Asset Group Id"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'created_at.desc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_assetsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_asset_groups":{"post":{"operationId":"list_asset_groups","summary":"List asset groups (folders for assets) with id and title. Use for \"What asset groups exist in Screenly\".","description":"List asset groups (folders for assets) with id and title. Use for \"What asset groups exist in Screenly\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'title.asc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_asset_groupsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_playlists":{"post":{"operationId":"list_playlists","summary":"List playlists with title, enabled flag, priority flag, schedule predicate and transition. Use for \"Which Screenly playl","description":"List playlists with title, enabled flag, priority flag, schedule predicate and transition. Use for \"Which Screenly playlists are enabled\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"is_enabled":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on enabled state in PostgREST syntax, for example 'eq.true'.","title":"Is Enabled"},"title":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on title in PostgREST syntax, for example 'ilike.*promo*'.","title":"Title"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'title.asc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_playlistsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_playlist_items":{"post":{"operationId":"list_playlist_items","summary":"List the items of playlists: which asset, in what position and for how many seconds. Use for \"What does my Screenly play","description":"List the items of playlists: which asset, in what position and for how many seconds. Use for \"What does my Screenly playlist play, in order\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"playlist_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on playlist id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Playlist Id"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'position.asc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_playlist_itemsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_labels":{"post":{"operationId":"list_labels","summary":"List labels used to group screens and schedule playlists, with name and type (all-screens, manual or screen). Use for \"W","description":"List labels used to group screens and schedule playlists, with name and type (all-screens, manual or screen). Use for \"Which Screenly labels do I have\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"type":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on label type in PostgREST syntax, for example 'eq.manual'.","title":"Type"},"order":{"anyOf":[{"maxLength":60,"type":"string"},{"type":"null"}],"default":null,"description":"Sort as column.direction, for example 'name.asc'.","title":"Order"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_labelsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_screen_labels":{"post":{"operationId":"list_screen_labels","summary":"List which labels are attached to which screens (pairs of label id and screen id). Use for \"Which screens carry which Sc","description":"List which labels are attached to which screens (pairs of label id and screen id). Use for \"Which screens carry which Screenly labels\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"label_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on label id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Label Id"},"screen_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on screen id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Screen Id"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_screen_labelsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_playlist_labels":{"post":{"operationId":"list_playlist_labels","summary":"List which labels are attached to which playlists (pairs of label id and playlist id). Use for \"Which labels is my Scree","description":"List which labels are attached to which playlists (pairs of label id and playlist id). Use for \"Which labels is my Screenly playlist scheduled on\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"label_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on label id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Label Id"},"playlist_id":{"anyOf":[{"maxLength":100,"type":"string"},{"type":"null"}],"default":null,"description":"Filter on playlist id in PostgREST syntax, for example 'eq.01HC9RFEFP1ATEH5ZT5VQMF65P'.","title":"Playlist Id"},"limit":{"anyOf":[{"maximum":1000,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"Maximum rows to return (PostgREST limit; keep at 100 or less).","title":"Limit"},"offset":{"anyOf":[{"maximum":100000,"minimum":0,"type":"integer"},{"type":"null"}],"default":0,"description":"Number of rows to skip.","title":"Offset"}},"title":"list_playlist_labelsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}}}}