{"$schema":"https://wellknown.network/schemas/agent-record-v1.json","schemaVersion":"1","id":"ag_c89j42mv92uq","handle":"streamloop","url":"https://wellknown.network/agents/streamloop","links":{"self":"https://wellknown.network/agents/streamloop/record.json","html":"https://wellknown.network/agents/streamloop","markdown":"https://wellknown.network/agents/streamloop/record.md","api":"https://wellknown.network/api/v1/agents/streamloop","status":"https://wellknown.network/api/v1/agents/streamloop/status","claim":"https://wellknown.network/agents/streamloop/claim","claimApi":"https://wellknown.network/api/v1/claims","claimDescriptor":"https://wellknown.network/agents/streamloop/claim.json","badge":"https://wellknown.network/agents/streamloop/badge.svg","openapi":"https://wellknown.network/openapi.json","history":"https://wellknown.network/api/v1/agents/streamloop/history","tools":"https://wellknown.network/api/v1/agents/streamloop/tools"},"ard":{"identifier":"urn:air:mcp.streamloop.app:agent:streamloop","type":"application/a2a-agent-card+json"},"kind":"agent","declared":{"name":"Streamloop","summary":"Hosted live-streaming backend: loop a video or playlist to YouTube, Twitch, Facebook Live, or a custom RTMP endpoint 24/7, up to 4K/60fps, with no operator intervention.","description":"Hosted live-streaming backend: loop a video or playlist to YouTube, Twitch, Facebook Live, or a custom RTMP endpoint 24/7, up to 4K/60fps, with no operator intervention.","publisher":{"name":"Streamloop","url":"https://streamloop.app"},"homepage":"https://streamloop.app/docs","repository":null,"version":"1.0.0","license":null,"protocols":["a2a","mcp"],"tags":["streaming","rtmp","youtube","twitch","facebook","loop","status","monitoring","playlist","hot-replace"],"pricing":null,"endpoints":[{"url":"https://mcp.streamloop.app/mcp","type":"mcp_streamable_http","auth":null,"probeable":true}],"skills":[{"id":"create-loop-stream","name":"Create loop stream","tags":["streaming","rtmp","youtube","twitch","facebook","loop"],"description":"Point a source video or playlist at a destination (YouTube, Twitch, Facebook Live, or custom RTMP) and loop it 24/7 up to 4K/60fps."},{"id":"stream-status","name":"Get stream status","tags":["status","monitoring"],"description":"Report the live/health state of a running stream."},{"id":"manage-playlist","name":"Manage playlist live","tags":["playlist","hot-replace"],"description":"Add, replace, or reorder videos and audio while a stream is live; changes apply almost instantly."}],"tools":["Create loop stream","Get stream status","Manage playlist live"],"extra":{"updatedAt":"2026-10-08T16:27:23.689551Z","inputModes":["application/json","text/plain"],"outputModes":["application/json","text/plain"],"publishedAt":"2026-10-08T16:27:23.689551Z","capabilities":{"streaming":true,"pushNotifications":false,"stateTransitionHistory":false},"registryName":"io.github.streamloop/mcp","protocolVersion":"0.3.0"},"attribution":{"kind":"a2a_card","name":"a2a_card","summary":"a2a_card","version":"a2a_card","description":"a2a_card","homepageUrl":"a2a_card","publisherUrl":"a2a_card","publisherName":"a2a_card"}},"derived":{"capabilities":[{"slug":"communication.sms-voice","name":"SMS & Voice","confidence":1,"provenance":"derived"},{"slug":"analytics.reporting","name":"Reporting & Dashboards","confidence":1,"provenance":"derived"},{"slug":"dev.monitoring","name":"Monitoring & Observability","confidence":1,"provenance":"declared"},{"slug":"automation.scheduling","name":"Scheduling & Cron","confidence":0.54,"provenance":"derived"},{"slug":"content.writing","name":"Writing & Editing","confidence":0.51,"provenance":"derived"},{"slug":"communication.chat","name":"Team Chat","confidence":0.51,"provenance":"derived"},{"slug":"security.secrets","name":"Secrets Management","confidence":0.51,"provenance":"derived"}],"categories":["analytics","automation","communication","content","dev","security"],"language":"en"},"observed":{"status":"live","statusReason":"Responded 2h ago.","lastOkAt":"2026-10-19T13:26:40.911Z","lastProbedAt":"2026-10-19T13:26:40.911Z","statusComputedAt":"2026-10-19T13:29:55.379Z","reliability30d":{"probes":31,"successRate":1,"p50Ms":214,"basis":"service","measures":{"availability":"availability","latency":"response time","tools":"tool surface observed","summary":"Checks reached the service itself."},"checks":{"total":31,"ok":31,"authBoundaryOk":0,"serviceOk":31,"note":"Counted from the observation rows for the window, checks of the server only (HTTP, A2A card, MCP initialize). ok = authBoundaryOk + serviceOk. `probes` is the sum of daily rollups and includes registry checks, so it can differ from `total`."}},"latestObservations":[{"at":"2026-10-19T13:26:40.911Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":209,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-19T06:25:09.421Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":238,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-18T23:29:45.805Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":224,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-18T16:35:17.419Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":244,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-18T09:27:53.137Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":420,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-18T02:24:40.586Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":210,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-17T19:27:05.743Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":214,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-17T13:25:17.421Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":296,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-17T06:21:49.360Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":243,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}},{"at":"2026-10-16T23:25:30.074Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":198,"error":null,"detail":{"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"toolCount":67,"toolsHash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","serverName":"streamloop-mcp","capabilities":["resources","tools"],"serverVersion":"0.1.0","protocolVersion":"2025-06-18"}}],"tools":[{"name":"list_streams","description":"Find streams and their ids — the starting point for every other stream tool. Each row carries the name, current state, scheduled start and whether that schedule"},{"name":"get_stream","description":"One stream's full configuration: current state, output quality and framerate, the destinations it publishes to (each enabled or not, with its delivery state), a"},{"name":"start_stream","description":"Start streaming now, looping the stream's playlist (or playing its scene) until it is stopped. THIS PUTS VIDEO IN FRONT OF THE PUBLIC, so confirm with the user "},{"name":"stop_stream","description":"Stop a stream that is live or starting. It stops publishing and becomes inactive; nothing is deleted and it can be started again with the same configuration. Do"},{"name":"delete_stream","description":"Permanently delete a stream, its playlists and its schedule. Irreversible, and it cannot be undone by re-creating the stream: uploads survive but the arrangemen"},{"name":"create_stream","description":"Use this to set up a new loop or a stream for a scene. The stream is created empty and CANNOT start until it has (1) a destination — add_stream_destination with"},{"name":"update_stream","description":"Change a stream's settings (name, quality, framerate, duration, storage, backup ingest) and/or its YouTube broadcast settings via the `youtube` object. Where it"},{"name":"schedule_stream","description":"Set the window a stream runs in, once or on a repeat, and arm it. The stream must already be startable — a destination plus either a playable video playlist or "},{"name":"cancel_stream_schedule","description":"Disarm a scheduled stream and return it to an unscheduled, inactive state, clearing any daily or weekly repeat. Use this to stop a recurring stream coming back;"},{"name":"check_stream_readiness","description":"Answer 'would start_stream work right now?' without changing anything. Runs the same pre-flight configuration checks a start does and returns ready plus every b"},{"name":"get_stream_live_stats","description":"How a live stream is doing ON YOUTUBE: watch URL, broadcast status, concurrent viewers, views and likes. Only meaningful while the stream is live to a YouTube c"},{"name":"list_stream_destinations","description":"Where a stream publishes, in the order they were added: each destination, whether it is enabled, and while the stream runs its delivery state (connecting, live,"},{"name":"add_stream_destination","description":"Make a stream also publish to one of the workspace's destinations (list_destinations), enabled. Up to 5 per stream and one YouTube channel at most (DESTINATION_"},{"name":"set_stream_destination_enabled","description":"Stop or resume sending to one of a stream's destinations without removing it. Disabling works while the stream is live — that output goes off the air at once — "},{"name":"remove_stream_destination","description":"Take a destination off a stream (the destination itself stays in the workspace). Refused while the stream is live (STREAM_LIVE): disable it with set_stream_dest"},{"name":"get_connection_hints","description":"Use this FIRST when the user names a platform they want to stream to (\"put this on YouTube\", \"also send it to Twitch\") and there is no destination for it yet. R"},{"name":"list_destinations","description":"Find the places this workspace can publish to — connected YouTube channels and custom RTMP endpoints — and their ids, which is what add_stream_destination needs"},{"name":"create_rtmp_destination","description":"Create a destination for any platform that gives out an RTMP ingest URL and stream key (Twitch, Facebook, Kick, X, TikTok, Telegram, a self-hosted server, or Yo"},{"name":"update_destination","description":"Maintain an existing destination: rename it, replace the stream key after the platform rotated it (custom RTMP only — a connected YouTube channel has no key to "},{"name":"start_youtube_connection","description":"Begin connecting a Google account so its YouTube channels can be streamed to with managed broadcasts (titles, privacy, thumbnails, live stats). Returns a Google"},{"name":"list_youtube_channels","description":"The YouTube channels this workspace has Google consent for, with live channel data (title, handle, country, subscriber count, connection status). These are NOT "},{"name":"create_youtube_destination","description":"Turn an already-consented YouTube channel into a destination a stream can publish to, with managed broadcasts (update_stream's `youtube` settings, get_stream_li"},{"name":"list_playlists","description":"Use this to get from a stream to something you can edit: pass streamId and you get the two playlists that stream owns — one video, one audio, created empty with"},{"name":"create_playlist","description":"An empty playlist owned by a scene, for one of its playlist sources to play (a stream's own two playlists come with the stream). Fill it with apply_playlist_ope"},{"name":"get_playlist","description":"Use this before editing a playlist (item ids for remove and reorder come from here, and so does the `version` the edit tools take) and after swapping one onto a"},{"name":"apply_playlist_operations","description":"Use this for every playlist change: add media, remove items, reorder, or switch between sequential and shuffle, as one ordered batch. All-or-nothing — if any op"},{"name":"copy_playlist","description":"Use this to reuse an arrangement on a second stream instead of rebuilding it: copies one playlist's contents into another playlist of the same kind. The target "},{"name":"swap_live_playlist","description":"Use this ONLY to put an edited playlist on the air while its stream is LIVE — the hot swap the product calls publishing. The stream changes over to the new arra"},{"name":"list_playlist_orders","description":"Find saved custom playback orders (order sequencers) and their ids. Use it before creating one — an order the user already has can be assigned to another playli"},{"name":"get_playlist_order","description":"One saved order: its description, how many playlists use it, and its newest usable version with any validation problems. Pass playlistId as well to get the answ"},{"name":"create_playlist_order","description":"Describe a playback order in plain language and have one written and validated. Pass the playlist it is for as playlistId: the order is written against that pla"},{"name":"refine_playlist_order","description":"Continue the conversation about an existing order — 'never end on an instrumental', 'put the announcement second instead' — producing a new version. Use this ra"},{"name":"assign_playlist_order","description":"Make a playlist play in a saved order. This is the step that changes playback, and unlike a playlist edit it needs no swap_live_playlist — a running stream pick"},{"name":"unassign_playlist_order","description":"Stop a playlist using a custom order; it returns to playing in its own item order (or shuffled, per the playlist's mode). The order itself is kept and can be as"},{"name":"list_uploads","description":"Find media and their ids (obj_...) — what apply_playlist_operations adds to a playlist. Removed media is not listed. `uploaded` false means the media is still a"},{"name":"get_upload","description":"One media file in detail: duration, resolution, framerate, whether it has video and audio (probed from the file itself, not from its name), a temporary download"},{"name":"create_upload","description":"Step 1 of uploading a LOCAL file: reserves the media record and returns `uploadUrl`, a presigned PUT you can use immediately. This server does not relay bytes, "},{"name":"complete_upload","description":"Step 2 of uploading a local file: call it once the bytes have been PUT to the url create_upload returned — by you, or by the user — which starts processing. Unt"},{"name":"discover_external_media","description":"Look at any media url and report what could be imported from it: each asset with its quality options, sizes and duration. REQUIRED BEFORE import_upload_from_url"},{"name":"import_upload_from_url","description":"Import chosen assets from a media url — a page, a direct file link, or a file the user attached in this conversation — straight into the workspace, with no loca"},{"name":"delete_upload","description":"Permanently remove a media file from the library: its stored bytes and every file derived from it are deleted. Irreversible. An upload that never finished (no c"},{"name":"get_billing_overview","description":"Use this to answer 'can this keep streaming, and for how long' — and whenever a stream fails to start or stops with no configuration problem, since check_stream"},{"name":"get_streaming_usage","description":"Use this for questions about the past — 'how many hours did I stream last month', 'is my spend going up' — not about the present. Returns minutes streamed, cred"},{"name":"get_account","description":"Who this token belongs to: the signed-in account's id, email, name, language and the default run-length new streams inherit. Use it to confirm which account an "},{"name":"list_workspaces","description":"Every workspace this account belongs to, with the account's role in each and which one is currently in use. Streams, media, playlists, destinations and credits "},{"name":"select_workspace","description":"Switch which workspace this connection works in, for every later tool call on this connection (other connections, even ones sharing the same login, are unaffect"},{"name":"get_selected_workspace","description":"Which workspace this connection is working in right now, and where that came from: `explicit` (a select_workspace call), `header` or `env` (the client pinned it"},{"name":"scene_get","description":"Read the scene's draft (or a published version, with version): a resource (with its revision and children, the sub-paths to read next), a type such as element/T"},{"name":"scene_probe","description":"Fetch a URL once, changing nothing in the show: HTTP status, content type, an outline of the JSON (keys, their values, array lengths) or the page's title and te"},{"name":"scene_remove","description":"Delete whole resources (frames, layers, sources, components). All or nothing: anything in use by something not removed in the same call is refused, with what us"},{"name":"scene_set","description":"Create, replace or change one resource; get <type> shows what each takes, with an example. value is the whole resource, as get answers it: a frame { code: \"<JSX"},{"name":"list_scenes","description":"Lists the workspace's scenes, newest first: id, name, the version last published (0: never) and when. Read one's draft with scene_get (path \"\" lists what it hol"},{"name":"create_scene","description":"Creates a scene with an empty draft, nothing published. Build it with scene_set (frame/<id> for each frame, source/… for what it reads), then publish_scene. Eac"},{"name":"publish_scene","description":"Publishes the draft exactly as it was at draftRevision (required) as the scene's next version: what streams playing it play from then on. All of it is checked f"},{"name":"discard_scene_draft","description":"Puts the draft back to the published version: every change made since it was published is lost (nothing on air changes). draftRevision (required) is the draft y"},{"name":"list_scene_versions","description":"Lists a scene's published versions, newest first. Answers items (version, publishedAt, publishedBy), nextCursor and hasMore. Read one with scene_get and version"},{"name":"revert_scene","description":"Publishes an earlier version's document as the next version (the versions in between stay; the draft is untouched — publishing the draft later is refused with S"},{"name":"delete_scene","description":"Deletes the scene, its draft and every published version, for good. Refused (SCENE_IN_USE) while a stream plays it. Its ingest keys are revoked and its cameras "},{"name":"set_stream_scene","description":"Makes a stream play a scene (its published version) instead of a video playlist, or with scene null stops doing so. Refused (STREAM_LIVE) while the stream runs:"},{"name":"get_scene_state","description":"What a scene has on air. Answers streams: each stream that plays it, with its id (stream), name and state and, under onAir while it runs, the frame/<id> on air "},{"name":"control_scene","description":"Acts on the scene on air, as its operator would: goFrame (take frame/<target> to air, with a transition), next (cue frame/<target> so the take is instant; no ta"},{"name":"create_scene_ingest_key","description":"Makes the key an encoder (OBS, vMix, a phone app) sends a live feed with, for one of the scene's rtmp or srt sources: RTMP, RTMPS and SRT URLs with the key, sho"},{"name":"rename_scene","description":"Changes the scene's display name, the one list_scenes and the dashboard show. Its draft, published versions and the streams playing it are untouched. Answers th"},{"name":"list_scene_inputs","description":"Lists a scene's ingest keys (id ingkey_…, which source, live or not, never the key itself), its secrets (names only) and its IP cameras: what create_scene_inges"},{"name":"revoke_scene_ingest_key","description":"Revokes an ingest key for good: the encoder using it is cut off at once. It cannot be restored; a new key for the same source: create_scene_ingest_key. Answers "},{"name":"delete_scene_secret","description":"Deletes a saved secret for good: its value cannot be read back, and a table that names it (\"$secret:<name>\") stops getting it. Only set_scene_secret with the ke"},{"name":"set_scene_secret","description":"Saves an API key or token a scene's tables send (sealed; never shown again). A table names it as \"$secret:<name>\" in a header value or a URL's query. A name tha"}],"package":null,"toolSurface":{"id":"ts_zk7nvbst7tj4","endpointId":"ep_kraqxv9uqs7s","hash":"dd1a73fd9c52203c06c70a2aacc78af196fc68b87926153d374ab4937e3269d1","toolCount":67,"serverName":"streamloop-mcp","serverVersion":"0.1.0","protocolVersion":"2025-06-18","firstSeenAt":"2026-10-15T22:27:39.013Z","lastSeenAt":"2026-10-19T13:26:40.917Z","observations":14,"toolNames":["list_streams","get_stream","start_stream","stop_stream","delete_stream","create_stream","update_stream","schedule_stream","cancel_stream_schedule","check_stream_readiness","get_stream_live_stats","list_stream_destinations","add_stream_destination","set_stream_destination_enabled","remove_stream_destination","get_connection_hints","list_destinations","create_rtmp_destination","update_destination","start_youtube_connection","list_youtube_channels","create_youtube_destination","list_playlists","create_playlist","get_playlist","apply_playlist_operations","copy_playlist","swap_live_playlist","list_playlist_orders","get_playlist_order","create_playlist_order","refine_playlist_order","assign_playlist_order","unassign_playlist_order","list_uploads","get_upload","create_upload","complete_upload","discover_external_media","import_upload_from_url","delete_upload","get_billing_overview","get_streaming_usage","get_account","list_workspaces","select_workspace","get_selected_workspace","scene_get","scene_probe","scene_remove","scene_set","list_scenes","create_scene","publish_scene","discard_scene_draft","list_scene_versions","revert_scene","delete_scene","set_stream_scene","get_scene_state","control_scene","create_scene_ingest_key","rename_scene","list_scene_inputs","revoke_scene_ingest_key","delete_scene_secret","set_scene_secret"],"distinctSurfaces":6},"endpointFacts":[{"id":"ep_kraqxv9uqs7s","url":"https://mcp.streamloop.app/mcp","type":"mcp_streamable_http","factsCheckedAt":"2026-10-18T16:35:17.432Z","auth":{"observedAt":"2026-10-18T16:35:17.716Z","authRequired":false,"scheme":null,"resourceMetadata":{"url":"https://mcp.streamloop.app/.well-known/oauth-protected-resource/mcp","resource":"https://mcp.streamloop.app/mcp","authorizationServers":["https://auth.streamloop.app"],"scopesSupported":["streamloop:read","streamloop:write","streamloop:destructive"]},"authorizationServer":{"url":"https://auth.streamloop.app/.well-known/oauth-authorization-server","issuer":"https://auth.streamloop.app","grantTypesSupported":["authorization_code","refresh_token"],"codeChallengeMethodsSupported":["S256"],"tokenEndpointAuthMethodsSupported":["none","client_secret_basic","client_secret_post"],"dynamicClientRegistration":true,"dpopSigningAlgValuesSupported":[],"clientIdMetadataDocumentSupported":null},"conformance":{"dpop":false,"rfc8414":true,"rfc9728":true,"pkceS256":true,"clientIdMetadataDocument":false,"dynamicClientRegistration":true}},"tls":{"observedAt":"2026-10-18T16:35:17.735Z","protocol":"TLSv1.3","chainValid":true,"chainError":null,"hostMatches":true,"subject":"streamloop.app","issuer":{"commonName":"WE1","organization":"Google Trust Services"},"validFrom":"2026-09-28T18:48:04.000Z","validTo":"2026-12-27T19:48:02.000Z","daysToExpiry":69,"sanCount":2,"fingerprint256":"AA:9A:57:99:05:4F:04:53:75:86:44:19:FC:D9:A7:F2:FB:46:A5:65:1E:2F:B4:A4:96:6F:53:BF:DC:41:1D:BC"}}]},"verification":{"claimed":false,"claimedAt":null,"proofs":[]},"provenance":{"sources":[{"source":"a2a_card","key":"https://streamloop.app/.well-known/agent-card.json","url":"https://streamloop.app/.well-known/agent-card.json","firstSeenAt":"2026-10-11T08:21:03.196Z","fetchedAt":"2026-10-11T08:21:03.196Z","normalizedAt":"2026-10-11T08:21:03.196Z"},{"source":"mcp_registry","key":"io.github.streamloop/mcp","url":"https://registry.modelcontextprotocol.io/v0/servers/io.github.streamloop%2Fmcp","firstSeenAt":"2026-10-11T08:20:00.841Z","fetchedAt":"2026-10-17T08:19:26.156Z","normalizedAt":"2026-10-17T08:19:26.156Z"}]},"firstSeenAt":"2026-10-11T08:20:00.841Z","updatedAt":"2026-10-19T13:31:27.903Z"}