{
  "openapi": "3.0.1",
  "info": {
    "title": "Video Frame Extractor & Scene Chunks for RAG",
    "description": "Video scene detection for direct video file links. Each scene is one row: a keyframe image, start and end time, and the transcript for that stretch from your own subtitles, token-counted for RAG. It does not transcribe. Not affiliated with any video platform.",
    "version": "1.0",
    "x-build-id": "YBW6zu54HYMJI5YdA"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/mmdincer~video-frame-extractor/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-mmdincer-video-frame-extractor",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/mmdincer~video-frame-extractor/runs": {
      "post": {
        "operationId": "runs-sync-mmdincer-video-frame-extractor",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/mmdincer~video-frame-extractor/run-sync": {
      "post": {
        "operationId": "run-sync-mmdincer-video-frame-extractor",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "videoUrls": {
            "title": "Video URLs",
            "maxItems": 50,
            "type": "array",
            "description": "Direct links to video files, one per line. Up to 50 per run. The link must return the file itself (an <code>https://…/clip.mp4</code> link), not a page with a video player. Links to YouTube, Vimeo, TikTok and similar pages are rejected.",
            "items": {
              "type": "string"
            }
          },
          "datasetId": {
            "title": "Read video links from a dataset",
            "type": "string",
            "description": "Optional. Pick an Apify dataset whose items contain direct video links. The Actor looks for <code>videoUrl</code>, <code>mediaUrl</code>, <code>fileUrl</code>, <code>url</code>, <code>link</code> and similar fields, so it can follow a scraper without copying links by hand. The dataset is opened read-only."
          },
          "segmentation": {
            "title": "How to split the video",
            "enum": [
              "scenes",
              "interval"
            ],
            "type": "string",
            "description": "<b>Scene changes</b> finds the cuts and returns one row per scene. <b>Fixed intervals</b> returns one row every N seconds, which suits lectures, webcams and screen recordings that have no real cuts.",
            "default": "scenes"
          },
          "sceneThreshold": {
            "title": "Scene change sensitivity",
            "minimum": 0.05,
            "maximum": 0.9,
            "type": "number",
            "description": "How different two frames must be to count as a cut, from 0.05 to 0.9. <b>Lower finds more scenes</b>, higher finds fewer. 0.3 is a good default; try 0.15 for soft transitions and 0.5 for noisy footage.",
            "default": 0.3
          },
          "intervalSeconds": {
            "title": "Interval length (seconds)",
            "minimum": 2,
            "maximum": 3600,
            "type": "integer",
            "description": "Used only with fixed intervals: one row every this many seconds.",
            "default": 30
          },
          "minSceneSeconds": {
            "title": "Shortest scene (seconds)",
            "minimum": 0.5,
            "maximum": 600,
            "type": "number",
            "description": "A scene shorter than this is joined to its neighbour, so a flash or a fade does not become its own row. 2 seconds by default.",
            "default": 2
          },
          "maxSceneSeconds": {
            "title": "Longest scene (seconds)",
            "minimum": 5,
            "maximum": 3600,
            "type": "number",
            "description": "A scene longer than this is cut into equal parts, so one long shot still gets regular keyframes. 60 seconds by default.",
            "default": 60
          },
          "maxScenesPerVideo": {
            "title": "Maximum scenes per video",
            "minimum": 1,
            "maximum": 500,
            "type": "integer",
            "description": "Safety cap on rows for one video. When a video has more cuts, the weakest cuts are dropped first. It also caps what one video can cost.",
            "default": 200
          },
          "mergeSimilarFrames": {
            "title": "Merge scenes that look the same",
            "type": "boolean",
            "description": "Join neighbouring scenes whose keyframes show the same shot (a fade, an animated overlay, a flicker the detector counted as a cut). Applies to scene changes only, never to fixed intervals, and needs keyframes. You are charged for the scenes that remain.",
            "default": true
          },
          "includeKeyframes": {
            "title": "Include keyframes",
            "type": "boolean",
            "description": "Save one JPEG per scene to the key-value store and add its link to every row. Turn it off for a transcript-only timeline (scene merging is then off too).",
            "default": true
          },
          "keyframeWidth": {
            "title": "Keyframe width (pixels)",
            "minimum": 160,
            "maximum": 1920,
            "type": "integer",
            "description": "Width of the saved JPEG, never larger than the video itself. 640 is enough for most vision models; use 1280 for small text on slides.",
            "default": 640
          },
          "contactSheet": {
            "title": "Contact sheet",
            "type": "boolean",
            "description": "Also save one overview image per video: a grid of keyframes with start times. Free.",
            "default": true
          },
          "transcriptDatasetId": {
            "title": "Transcripts from a dataset",
            "type": "string",
            "description": "Optional. Pick the dataset of a transcription run, for example one from <b>audio-video-transcriber</b>. Rows are matched to videos by the <code>url</code> field and their <code>segments</code> are aligned to the scenes. Nothing is transcribed here."
          },
          "subtitleUrls": {
            "title": "Subtitle files",
            "type": "object",
            "description": "Optional. A JSON object that maps a video link to its subtitle file (.srt or .vtt): <code>{\"https://example.com/talk.mp4\": \"https://example.com/talk.vtt\"}</code>. A subtitle file you give wins over every other transcript source.",
            "default": {}
          },
          "useEmbeddedSubtitles": {
            "title": "Use subtitles inside the video",
            "type": "boolean",
            "description": "When no subtitle file or dataset covers a video, read a text subtitle track from the file itself (MKV, MP4 and WebM can carry one). Picture subtitles from discs cannot be read.",
            "default": true
          },
          "chunkSize": {
            "title": "Chunk size (tokens)",
            "minimum": 64,
            "maximum": 4096,
            "type": "integer",
            "description": "Largest transcript text per row, counted with the cl100k_base tokenizer that OpenAI models use. A scene with more speech is split into several rows that share its keyframe. 512 is a good default for retrieval.",
            "default": 512
          },
          "maxVideos": {
            "title": "Maximum videos per run",
            "minimum": 1,
            "maximum": 50,
            "type": "integer",
            "description": "Upper bound on how many videos are processed in one run, applied after the list and the dataset are merged. A low number is a simple way to cap the cost of a first run.",
            "default": 50
          },
          "maxDurationMinutes": {
            "title": "Longest video to analyse (minutes)",
            "minimum": 1,
            "maximum": 180,
            "type": "integer",
            "description": "Only the first this-many minutes of a longer video are copied, analysed and billed. The rest of a longer file is not downloaded. The video row says so in <code>truncated</code>. 60 minutes by default; the prefilled run uses 5 to stay cheap.",
            "default": 60
          },
          "maxFileSizeMb": {
            "title": "Maximum file size (MB)",
            "minimum": 1,
            "maximum": 1000,
            "type": "integer",
            "description": "Skip a video larger than this instead of downloading it. Files are streamed to disk, so memory is not the limit, but a huge download takes time.",
            "default": 500
          },
          "proxyConfiguration": {
            "title": "Proxy configuration",
            "type": "object",
            "description": "Optional. Videos are downloaded directly, which works for most hosts. Use Apify Proxy only when a file sits behind a CDN that blocks datacenter IPs. A server that answers 403 or 429 is not retried or worked around."
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}