Home > Dev > Docs
Home / Pricing / Docs / Apps

비디오스튜 개발자 문서

요청 형식 주의사항 POST 요청 시 Content-Type: application/json 헤더와 함께 JSON body를 그대로 전달하는 방식을 권장합니다. application/x-www-form-urlencoded를 사용할 경우에는 파라미터를 JSON으로 직렬화한 뒤 payload 필드에 담아 전송하십시오. 예: payload={"apiKey":"...","secret":"..."}

이 문서 예시의 JSON에 붙은 // 주석은 설명용입니다. 표준 JSON은 주석을 허용하지 않으므로, 실제 요청 본문에는 주석을 넣지 마세요. (주석이 포함된 블록은 jsonc로 표기했습니다.)

Automation API

편집 화면 없이 동영상을 자동으로 생성·추출하는 API입니다. 토큰 노출 방지를 위해 반드시 백엔드에서만 호출하십시오.

POST https://videostew.com/api/automations

프로젝트 생성과 추출을 동시에 자동화합니다. 완료된 최종 결과는 webhookUrl 또는 앱 설정의 Export Webhook으로 POST 전달됩니다. 이 방법으로 생성된 프로젝트는 추출 이후 일주일 후 자동으로 삭제됩니다.

인증 헤더

헤더 필수 설명
Authorization 계정 설정 > API 토큰에서 복사한 토큰. Bearer Qjky6mFiMkRn... 형식
x-nonce 각 요청에 대한 유니크한 값 (중복 요청 구분용)

바디 파라미터

파라미터 필수 타입 설명
injector object 데이터 주입/변형 명세. 아래 Injector 섹션 참고
dictionary object TTS/STT 텍스트 치환 규칙. 아래 dictionary 섹션 참고
baseProjectId string 특정 프로젝트를 템플릿으로 사용할 경우의 projectId. 같은 스페이스이거나 public 상태여야 함
spaceId int 대상 워크스페이스 고유번호. 0이면 기본 워크스페이스
type string 추출 파일 형식. mp4 | jpg
webhookUrl string 완료 시 결과를 전달할 URL. 콜백을 받을 서버가 없어 폴링만 사용할 경우 생략 가능(응답의 pollUrl로 대체)
webhookType string webhook 전달 방식. form | json. 폴링만 쓸 경우 불필요
webhookHeader string webhook 커스텀 헤더. 헤더명: 값 형식. 예: x-api-key: abc123. 폴링만 쓸 경우 불필요

호출 예시

curl -X POST "https://videostew.com/api/automations" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM" \
  -H "Content-Type: application/json" \
  -d '{
    "baseProjectId": "88282f69vmqbqr9",
    "injector": {
      "wizard": {
        "source": "url",
        "sourceContent": "https://doo39oi115k60.cloudfront.net/wizard-url-example/"
      }
    }
  }'

응답 예시

{
  "status": "done",
  "result": {
    "projectId": "abc123...",
    "pollUrl": "https://videostew.com/api/exports/abc123...",
    "pollIntervalSeconds": 180
  }
}

처리 결과 확인: 렌더링은 요청 시점에 즉시 끝나지 않으며, 최종 완료 여부는 아래 두 가지 방법 중 하나로 확인해야 합니다. 두 방법은 배타적이지 않으므로 필요하면 함께 사용해도 됩니다.

  1. Webhook (콜백을 받을 서버가 있는 경우)webhookUrl을 지정하면 완료/실패 시 해당 URL로 결과가 POST 전달됩니다.
  2. 폴링 (콜백을 받을 서버가 없는 경우, 예: AI/LLM이 직접 호출하는 자동화) — 요청 호스트가 없어 webhook을 받을 수 없다면, 응답에 포함된 pollUrl(= GET /api/exports/{projectId}, 아래 Exports API 섹션 참고)을 주기적으로 호출해 status를 확인하세요.
    • 권장 폴링 주기: 3분(180초) 이상. 응답의 pollIntervalSeconds 값을 그대로 사용하면 됩니다. 렌더링은 통상 수 분이 걸리므로 이보다 자주 조회해도 결과가 더 빨리 나오지 않으며, 서버 부하만 늘어납니다.
    • status 값: generate/request = 아직 처리 중, done = 완료(link 필드에 결과 URL), fail = 실패.
    • 사람이 직접 확인할 때는 https://videostew.com/v/{projectId} 접속으로도 진행 상황("추출중입니다" → 완성된 영상)을 볼 수 있지만, 이는 사람용 화면이며 자동화(코드) 연동에는 pollUrl 또는 webhookUrl을 사용하십시오.

Webhook 응답 (추출 완료 시)

{
  "status": "done",
  "projectId": "abc123...",
  "size": "1080x1920",
  "type": "mp4",
  "link": "https://cdn.videostew.com/projects/..."
}

폴링 응답 예시 (GET /api/exports/{projectId} 호출 시)

{
  "page": 1,
  "rows": [
    {
      "id": "e-19",
      "apiKey": "...",
      "spaceId": 0,
      "projectId": "abc123...",
      "status": "done",
      "size": "1080x1920",
      "scenario": "",
      "type": "mp4",
      "createdAt": "2026-07-09 12:00:00",
      "updatedAt": "2026-07-09 12:04:30",
      "link": "https://cdn.videostew.com/projects/..."
    }
  ]
}

statusdone이 될 때까지 pollIntervalSeconds(기본 3분) 간격으로 재조회하고, done이 되면 link로 결과를 받아오면 됩니다.


Injector 세부 옵션

데이터를 주입하는 방법으로 wizard, data를 제공하며, 각각은 배타적이므로 한 번에 한가지 방식만 사용할 수 있습니다.

injector.wizard

텍스트 또는 URL을 넘기면 AI가 분석해 동영상을 자동으로 만들어줍니다. 세부적인 제어는 어렵지만, 가장 간단하게 동영상을 생성할 수 있는 방법입니다.

파라미터 설명
source 소스 타입. text | url
sourceContent source에 대응하는 값. text면 HTML/plain text, url이면 URL 문자열
title 프로젝트 제목
language 프로젝트 언어. 예: ko, en, ja
opts.replace AI가 교체할 슬라이드 범위. body=본문만 교체, 인트로/아웃트로는 템플릿 그대로 유지(반복 사용하는 고정 애니메이션·엔딩에 적합). headbody=AI가 소제목을 자동 생성하며 소제목+본문 교체, 인트로/아웃트로 유지. all=인트로/아웃트로 포함 전체 교체
opts.visual 비주얼 소스 방식. stock-mixed/stock-video/stock-image=비디오스튜 스톡 라이브러리에서 맥락에 맞는 리소스를 자동 매칭(각각 혼합/비디오만/이미지만). ai-image=AI로 이미지 생성. none=비주얼 없음(원본 URL에 이미지가 풍부할 때 적합)
opts.autoLineBreak y로 설정하면 텍스트를 줄 단위로 분리해, 한 줄씩 등장하는 텍스트 애니메이션이 의도대로 동작합니다. 대부분의 템플릿이 이 애니메이션을 기본으로 사용하므로 y 권장
opts.visualStyle 비주얼 스타일. illust=디지털아트, photo=실사, flat-vector=벡터, editorial-cartoon=만평, editorial-illust=신문 일러스트, silhouette=실루엣. 또는 "수묵화 스타일로 그려줘" 처럼 직접 프롬프트를 입력해 원하는 스타일을 지정
opts.narrationVoices 대화형 콘텐츠(팟캐스트 등)에서 화자별 AI 목소리 지정. { "neutral": "libraryId", "화자명": "libraryId", ... } 형태의 객체. neutral은 화자 없는 슬라이드에 적용되는 기본 목소리. 화자명은 콘텐츠의 화자명: 패턴과 정확히 일치해야 함. 단일 TTS는 이 필드 대신 베이스 프로젝트의 나레이션 설정을 따름
adjust.duration 목표 분량. keep=원본 유지, 30s | 1m | 3m | 10m | 20m
adjust.structure 구조. keep=원본, body=본문만, headbody=소제목+내용 형식
adjust.style 스크립트 스타일. keep=원본 유지, colloquial=팟캐스트 같은 대화형, news=뉴스 방송처럼 공식적·객관적, info=정보 전달에 최적화된 명확·간결한 스타일, insight=인사이트와 분석을 강조하는 심층적 스타일, essay=서술적·사색적 에세이 톤, casual=친근하고 편안한 일상 대화 스타일. 또는 "시청자에게 말 걸듯 친근하게, 유머도 살짝 섞어줘" 처럼 직접 프롬프트를 입력해 원하는 스타일을 지정

adjust의 모든 키가 keep이면 원본 글을 AI로 다듬는 과정 없이 원문 그대로 사용합니다.

{
  "wizard": {
    "source": "url",
    "sourceContent": "https://doo39oi115k60.cloudfront.net/wizard-url-example/",
    "language": "ko",
    "opts": {
      "replace": "all",
      "visual": "ai-image",
      "visualStyle": "illust",
      "autoLineBreak": "y"
    },
    "adjust": {
      "duration": "1m",
      "structure": "headbody",
      "style": "news"
    }
  }
}

대화형(팟캐스트) 예시 - 화자별 AI 목소리 지정

콘텐츠에 진행자:, 게스트: 같은 화자 패턴이 포함된 경우, narrationVoices로 각 화자에 다른 목소리를 지정할 수 있습니다. 화자명은 콘텐츠의 패턴과 정확히 일치해야 합니다.

{
  "wizard": {
    "source": "text",
    "sourceContent": "<p>진행자: 안녕하세요, 오늘의 주제는...</p><p>게스트: 네, 반갑습니다...</p>",
    "language": "ko",
    "opts": {
      "replace": "all",
      "narrationVoices": {
        "neutral": "voice-library-id-default",
        "진행자": "voice-library-id-host",
        "게스트": "voice-library-id-guest"
      }
    }
  }
}

neutral: 화자 패턴이 없는 슬라이드(인트로·아웃트로 등)에 적용되는 기본 목소리입니다.

injector.data

프로젝트/슬라이드/요소 구조를 직접 지정합니다. 영상을 어떻게 만들 것인지 모든 것을 직접 구성할 때 사용합니다. 기존 요소와 일치하면 대체, 없으면 신규 생성합니다. 변경이 필요한 키만 지정하면 되며, 지정하지 않은 값은 기존 프로젝트의 값을 유지합니다.

라벨 ≠ API 키: 요소에 붙인 라벨이 img여도 이미지 주입 키는 항상 image입니다. 라벨(label)은 '어느 슬라이드/요소'인지 고르는 용도이고, 주입 키(text image video)와 좌표·스타일 키는 고정입니다.

data 키

최상위에 지정한 bgm은 slides 배열 전체에 기본값으로 적용됩니다. 각 슬라이드별 지정이 있으면 그 값을 더 우선시합니다.

설명
title 프로젝트 제목
language 프로젝트 언어. 예: ko, en
bgm 프로젝트 BGM 파일 URL
slides 슬라이드 배열

data.slides[] 키

설명
label 슬라이드 식별 라벨(기본 베이스 프로젝트내의 슬라이드 라벨기준으로 매칭). 같은 label을 여러 번 지정하면 해당 템플릿 슬라이드를 복제해 슬라이드 수를 늘릴 수 있습니다. 예: main 라벨을 3번 쓰면 main 슬라이드가 3개 생성. 라벨값은 편집화면에서 하단의 슬라이드 패널에서 확인할 수 있습니다.
narration 슬라이드 나레이션. 텍스트를 입력하면 템플릿에 설정된 AI 목소리로 읽어줍니다. 직접 녹음한 오디오를 쓰려면 공개 URL을 입력하세요
sound 슬라이드 효과음 URL
bgm 이 슬라이드에만 적용할 BGM URL. 최상위 bgm보다 우선
text 텍스트 요소 내용. 단순 문자열이면 슬라이드의 첫 번째 텍스트 요소에 적용. 슬라이드에 텍스트 요소가 여러 개 있을 때 각 요소를 정확히 타겟팅하려면 { "label": "요소라벨", "content": "내용" } 객체 형태로 배열 지정(라벨은 템플릿에서 설정한 요소 라벨 기준). 빈 문자열이면 요소 삭제. 이 간단 모드에서는 슬라이드 최상위 text/image/video 키만 씁니다. 요소 단위(위치·애니메이션·색 등) 제어가 필요하면 아래 상세 설정elements 배열을 사용하세요.
image 이미지 요소 libraryId. 배열로 여러 개 지정 가능
video 비디오 요소 libraryId. 배열로 여러 개 지정 가능

참고: URL을 지정하는 모든 필드(image, video, sound, bgm, narration 등)는 공개(public) 접근 가능한 주소여야 하며, 크롬 브라우저 기준의 표준 파일 형식이어야 합니다.

예시 1 - 텍스트·이미지 치환 + TTS 나레이션

{
  "data": {
    "language": "ko",
    "bgm": "https://example.com/bgm.mp3",  // 모든 슬라이드에 공통 적용
    "slides": [
      {
        "label": "title",                   // 베이스 프로젝트의 슬라이드 라벨로 매칭
        "text": "오늘의 뉴스 제목",           // 템플릿의 텍스트 요소를 이 내용으로 교체
        "image": "https://doo39oi115k60.cloudfront.net/wizard-url-example/01.webp",
        "narration": "오늘의 뉴스를 전해드립니다."  // 문자열이면 TTS로 생성(베이스 프로젝트의 나레이션 속성 따름)
      },
      {
        "label": "body",
        "text": "본문 내용입니다.",
        "image": "https://doo39oi115k60.cloudfront.net/wizard-url-example/02.webp"
      },
      {
        "label": "outro",
        "text": ""                          // 빈 문자열이면 해당 텍스트 요소 삭제
      }
    ]
  }
}

예시 2 - 라벨로 요소 타겟팅

템플릿에 텍스트 요소가 여러 개 있을 때, { label, content } 형태로 어떤 요소에 무엇을 넣을지 정확히 지정할 수 있습니다. 단, 이 방식은 Videostew 편집 화면에서 각 텍스트 요소에 미리 라벨을 붙여두어야 동작합니다. 라벨이 없는 요소는 타겟팅할 수 없습니다. 예를 들어 상단 요소에 title, 하단 AI 보이스용 요소에 voicetext라고 라벨을 붙여둔 템플릿이라면 아래처럼 각각 제어할 수 있습니다.

{
  "data": {
    "slides": [
      {
        "label": "main",
        "text": [
          { "label": "title", "content": "이거 진짜 될까?" },       // 화면 상단 타이틀 요소
          { "label": "voicetext", "content": "이거 진짜 될까" }     // AI 보이스가 읽을 자막 요소
        ]
      }
    ]
  }
}

예시 3 - 녹음 파일 나레이션 + 슬라이드별 비디오

{
  "data": {
    "slides": [
      {
        "label": "intro",
        "narration": "https://doo39oi115k60.cloudfront.net/wizard-url-example/narration1.mp3", // 직접 녹음/합성한 오디오 파일
        "video": "https://doo39oi115k60.cloudfront.net/wizard-url-example/video1.mp4"
      },
      {
        "label": "body",
        "narration": "https://doo39oi115k60.cloudfront.net/wizard-url-example/narration2.mp3", 
        "video": "https://doo39oi115k60.cloudfront.net/wizard-url-example/video2.mp4",
        "bgm": "https://example.com/this-slide-only.mp3"  // 이 슬라이드만 다른 BGM
      }
    ]
  }
}

injector.data 상세 설정 (elements)

injector.data의 확장 모드입니다. 위 간단 모드(text/image/video 문자열)로 표현하기 힘든 세부 제어(요소 위치, 같은 종류 요소 여러 개, 등장 애니메이션·제자리효과 등)가 필요할 때 elements 배열을 사용합니다. 아래는 사용 가능한 키의 전체 목록이며, 실제 요청에는 필요한 것만 포함하세요.

baseProjectId 필수: injection은 호출자가 소유한 프로젝트/템플릿을 베이스로 합니다. baseProjectId를 생략하면 요소가 반영되지 않으니 자신의 프로젝트 ID를 지정하세요. 베이스에 없는 새 슬라이드 레이아웃을 elements만으로 생성할 수는 없습니다.

color 포맷: [[R, G, B, A], degree] (R/G/B는 0-255, A는 0-1 불투명도, degree는 그라데이션 각도, 단색이면 0).

미디어 교체는 libraryId에 공개 URL: 이미지/비디오 요소의 libraryId에 public URL을 넣으면 인제스트되어 교체됩니다. custom.source나 요소의 image 키로는 교체되지 않습니다.

요소 등장 애니메이션 trans (요소 최상위 필드, 슬라이드 전환 trans와 별개. 형식 그룹__방향):

그룹 방향
slide flip_push flip_pull cube left right up down
stretch left right up down horizontal vertical
flip horizontal_left horizontal_right vertical_up vertical_down
reveal left right up down horizontal_open vertical_open
fade normal left right up down
zoom zoomspin in out
circle open
clock asc desc
blink (방향 없음)

요소 제자리효과 idle: pendulum pulse twitch updown leftright shake blink clockwise counterclockwise. 세기는 idleConf: { "speed": 수치, "distance": 수치 }.

슬라이드 전환과 요소 애니메이션은 값 체계가 다릅니다. 슬라이드 전환(slides[].trans.type)은 하이픈 방향(fade cube-ltr reveal-rtl 등), 요소 등장 애니메이션(elements[].trans.type)은 위 표의 언더바 방향(reveal__right 등)을 씁니다.

필드 표

슬라이드 레벨:

타입 설명
label string 베이스 슬라이드 라벨로 매칭(간단 모드와 동일)
trans object 슬라이드 전환효과 { type, durationTime }
narration object 나레이션(아래)
glb object 슬라이드 전역(BGM/효과음/배경/블러)
elements array 요소 배열. 라벨 일치 시 대체, 없으면 생성, content:""면 삭제

요소 elements[] 공통:

타입 설명
type string text | image | video | shape
label string 요소 라벨(대체 대상 선택)
content string 텍스트 내용(type:text). ""면 요소 삭제
libraryId string 미디어 소스. 공개 URL이면 인제스트되어 교체
rect object 위치·크기(아래)
custom object 스타일·등장효과(아래)
trans object 요소 등장 애니메이션 { type, txtRange }(위 표)
idle / idleConf string / object 제자리효과(위 목록)

rect:

설명
top left width height 위치·크기(px)
opacity 요소 불투명도 0-1
innerType 미디어 표시 cover(꽉 채움·기본) | contain(맞춤) | fill(원본비율)
innerPosition 포커스 위치, CSS position 형식(예: 50% 30%)

custom (텍스트):

설명
fontSize 글자 크기(px)
color / raColor 글자색 / 가독성배경 색 (color 포맷)
align 가로정렬 left | center | right
valign 세로정렬 top | middle | bottom
lineHeight 행간
raType 가독성 배경 "" | block | inline(기본) | outline | shadow
enabledTts true면 이 텍스트를 AI 보이스가 읽음
splitLine 텍스트 등장효과 "" | 1l | 2l | p
splitLineType replace(교체) | add(누적)

custom (비디오):

설명
trimStart trimEnd 트림(초)
speed volume 속도 / 볼륨
loop 반복(0=안함, 9999=무한)

narration:

설명
type voice(오디오 파일) | tts(텍스트 합성)
libraryId type:voice일 때 오디오 URL
content type:tts일 때 읽을 텍스트
volume speed trimStart trimEnd 볼륨 / 속도 / 트림

glb:

설명
bgmLibraryId bgmVolume bgmSpeed 슬라이드 BGM URL / 볼륨 / 속도
soundLibraryId soundVolume 효과음 URL / 볼륨
soundEvery true면 연속 슬라이드에서 반복 재생
soundFit true면 슬라이드 길이에 맞춰 페이드
backgroundColor 배경색 (color 포맷)
bgBlr bgBlrB 배경 블러 on/off / 강도 0-1
{
  "data": {
    "title": "프로젝트 제목",
    "language": "ko",
    "slides": [
      {
        "trans": {
          "type": "fade",       // auto | fade | flip-ltr | flip-ttb | cube-ltr | cube-rtl | reveal-ltr | reveal-rtl
          "durationTime": 0.3
        },
        "narration": {
          "type": "voice",      // voice(오디오 파일) | tts(텍스트 합성)
          "libraryId": "https://doo39oi115k60.cloudfront.net/wizard-url-example/narration1.mp3",  // type이 voice일 때
          "content": "",        // type이 tts일 때 읽을 텍스트
          "volume": 1,
          "speed": 1.1,
          "trimStart": 0,
          "trimEnd": 0
        },
        "glb": {
          "bgmLibraryId": "https://example.com/bgm.mp3",
          "bgmVolume": 0.9,
          "bgmSpeed": 1,
          "soundLibraryId": "https://example.com/sfx.mp3",
          "soundVolume": 1,
          "soundEvery": true,
          "soundFit": false,
          "backgroundColor": [[0, 0, 0, 1], 0],
          "bgBlr": false,
          "bgBlrB": 0.4
        },
        "elements": [
          {
            "type": "text",
            "content": "텍스트 내용",
            "rect": {
              "top": 800, "left": 40, "width": 1000, "height": 200,
              "opacity": 1
            },
            "custom": {
              "fontSize": 48,
              "color": [[255, 255, 255, 1], 0],
              "align": "center",          // left | center | right
              "valign": "middle",         // top | middle | bottom
              "lineHeight": 1.2,
              "raType": "shadow",         // "" | block | inline | outline | shadow  (기본 inline)
              "raColor": [[0, 0, 0, 1], 0],
              "enabledTts": true,
              "splitLine": "1l",          // "" 전체 | 1l 한 줄씩 | 2l 두 줄씩 | p 문단별
              "splitLineType": "replace"  // replace 교체 | add 누적
            },
            "trans": { "type": "reveal__right", "txtRange": "line" }  // 요소 등장 애니메이션(위 표)
          },
          {
            "type": "image",
            "libraryId": "https://doo39oi115k60.cloudfront.net/wizard-url-example/01.webp",
            "rect": {
              "top": 0, "left": 0, "width": 1080, "height": 1920,
              "opacity": 1,
              "innerType": "cover",       // cover | contain | fill
              "innerPosition": "50% 30%"  // CSS position 형식, 이미지 포커스 위치
            },
            "idle": "updown",             // 제자리효과(위 목록)
            "idleConf": { "speed": 1.0, "distance": 1.0 }
          },
          {
            "type": "video",
            "libraryId": "https://doo39oi115k60.cloudfront.net/wizard-url-example/video1.mp4",
            "rect": {
              "top": 0, "left": 0, "width": 1080, "height": 1080,
              "innerType": "cover",
              "innerPosition": "50% 50%"
            },
            "custom": {
              "trimStart": 0,
              "trimEnd": 10,
              "speed": 1,
              "volume": 1,
              "loop": 9999    // 0 = 반복 안함, 9999 = 무한 반복
            }
          },
          {
            "type": "shape",
            "libraryId": "shape-library-id",
            "rect": {
              "top": 0, "left": 0, "width": 200, "height": 200
            },
            "custom": {
              "color": [[255, 100, 0, 1], 0]
            }
          }
        ]
      }
    ]
  }
}

dictionary

TTS/STT 시 적용할 텍스트 치환 규칙입니다. injector와 함께 바디 최상위에 전달합니다. 스페이스 딕셔너리와 병합되며 여기서 지정한 값이 우선합니다. 영역당 최대 100개 항목.

설명
tts AI 보이스가 텍스트를 읽을 때 적용. 잘못 발음되는 단어를 올바른 발음으로 강제 지정
stt 음성을 텍스트로 변환(자막 생성)할 때 적용. STT가 잘못 인식하는 단어를 올바른 표기로 강제 교정
trans 번역 후처리 시 적용
{
  "injector": {
    "wizard": { "source": "url", "sourceContent": "https://doo39oi115k60.cloudfront.net/wizard-url-example/" }
  },
  "dictionary": {
    "tts": [
      { "i": "3D", "o": "쓰리디" },       // "삼디"로 읽히는 걸 방지
      { "i": "AI", "o": "에이아이" }       // "아이"로 읽히는 걸 방지
    ],
    "stt": [
      { "i": "video studio", "o": "videostew" },   // STT가 잘못 인식한 표기를 교정
      { "i": "비디오 스튜", "o": "비디오스튜" }     // 띄어쓰기 오인식 교정
    ]
  }
}

기타 API

GET https://videostew.com/api/spaces - 워크스페이스 목록 조회

curl -X GET "https://videostew.com/api/spaces" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM"

GET https://videostew.com/api/projects - 프로젝트 목록 조회

파라미터 타입 설명
spaceId int 대상 워크스페이스 고유번호. 0이면 기본 워크스페이스
projectIds string 콤마로 구분된 프로젝트 ID 목록
folderId int 폴더 고유번호. 기본값(루트) 1000000
status string public | enabled | secret. trash는 삭제된 상태
limit int 페이지당 항목수
page int 페이지 번호
title string 제목 검색
tags string 태그 검색
curl -X GET "https://videostew.com/api/projects?spaceId=0&limit=20&page=1" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM"

GET https://videostew.com/api/projects/:projectId - 단일 프로젝트 조회

curl -X GET "https://videostew.com/api/projects/PROJECT_ID" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM"

쿼리 파라미터: includeSlides=true - 응답 resultslides 배열이 포함됩니다(각 슬라이드: slideId glb duration narration trans elements note 등, 주입 구조와 대칭). 주입한 값의 실제 반영을 확인할 때 유용합니다. 대용량이므로 필요할 때만 사용하세요.

GET https://videostew.com/api/exports - 추출 목록 조회

특정 프로젝트의 추출만 조회하려면 projectId를 쿼리 파라미터가 아니라 **경로(path segment)**로 전달해야 합니다: GET /api/exports/{projectId} (아래 예시 참고).

파라미터 타입 설명
spaceId int 대상 워크스페이스 고유번호. 0이면 기본 워크스페이스
projectIds string 콤마로 구분된 프로젝트 ID 목록
type string mp4 | jpg
limit int 페이지당 항목수
page int 페이지 번호
curl -X GET "https://videostew.com/api/exports/PROJECT_ID?limit=20" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM"

GET https://videostew.com/api/exports/:projectId/:exportId - 단일 추출 조회

curl -X GET "https://videostew.com/api/exports/PROJECT_ID/EXPORT_ID" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM"

POST https://videostew.com/api/exports/:projectId - 추출 요청

파라미터 타입 설명
type string mp4 | jpg
webhookUrl string 완료 시 결과를 받을 URL
webhookType string form | json
webhookHeader string webhook 커스텀 헤더. 헤더명: 값 형식. 예: x-api-key: abc123
curl -X POST "https://videostew.com/api/exports/PROJECT_ID" \
  -H "Authorization: Bearer {{bearerToken}}" \
  -H "x-nonce: $RANDOM" \
  -H "Content-Type: application/json" \
  -d '{"type":"mp4","webhookUrl":"https://your-server.com/webhook"}'

응답:

{
  "status": "done",
  "result": {
    "id": "e-19",
    "projectId": "...",
    "status": "generate",
    "type": "mp4"
  }
}

Webhook 응답 (추출 완료 시):

{
  "status": "done",
  "projectId": "...",
  "size": "1280x720",
  "type": "mp4",
  "link": "https://cdn.videostew.com/projects/..."
}

SDK

SDK curl 예시에 인증정보를 자동으로 채우려면 앱 관리 페이지에서 앱을 먼저 발급하세요.

자사의 웹사이트에서 자사의 고객들에게 비디오스튜의 편집화면만 제공할 때 사용합니다.

인증 (액세스 토큰 발급/만료)

SDK를 사용할 때는 각 사용자마다 개별 액세스 토큰을 발급해야 합니다. 토큰은 마지막 사용 이후 1개월 간 유효하며, 재사용 시 자동 연장됩니다. 401 Token is invalid 응답이 오면 새 토큰을 발급해 fallback 처리하세요.

!! secret 키 노출 방지를 위해 반드시 백엔드에서만 요청하십시오.

POST https://videostew.com/auth/access-token - 액세스 토큰 발급

파라미터 필수 타입 설명
apiKey string 발급받은 앱의 ApiKey
secret string 발급받은 앱의 시크릿 키
uniqueId any 자사 플랫폼에서 사용하는 유저의 고유번호
language string uniqueId 신규 생성 시 언어 강제 지정. 예: ko, en
curl -X POST "https://videostew.com/auth/access-token" \
  -H "Content-Type: application/json" \
  -d '{
    "apiKey": "{{apiKey}}",
    "secret": "{{secret}}",
    "uniqueId": "user_123"
  }'

응답:

{
  "status": "done",
  "apiKey": "abc1de2fg3...",
  "token": "Qjky6mFiMkRnOmExYj..."
}

POST https://videostew.com/auth/revoke-access-token - 액세스 토큰 만료 (선택)

로그아웃 등 모든 활동 종료 시 해당 유저의 토큰을 강제 만료합니다. 토큰은 1회성이 아니므로 강제 삭제 시 사용 중인 다른 탭에서 문제가 발생할 수 있습니다. 사용자가 탈퇴 등으로 확실히 그만두는 시점에서 호출하시면 됩니다.

curl -X POST "https://videostew.com/auth/revoke-access-token" \
  -H "Content-Type: application/json" \
  -d '{
    "apiKey": "{{apiKey}}",
    "secret": "{{secret}}",
    "uniqueId": "user_123"
  }'

편집기 호출

videostewSDK.open(options)

버튼 클릭 등의 이벤트에서 편집기를 모달로 엽니다.

<script src="https://cdn.videostew.com/web/sdk/sdk-latest.js"></script>
<script>
	videostewSDK.open({
		token: "Qjky6mFiMkRnOmEx...", // /auth/access-token 응답의 token 값
		projectId: "...",     // 수정할 프로젝트 ID (없으면 신규 생성)
		// baseProjectId: "...",  // 특정 프로젝트를 템플릿으로 사용(신규 생성시)
		// language: "ko",        // 프로젝트 및 UI 언어 설정
		// injector: { ... },     // 데이터 주입/변형 명세
		// dictionary: { ... },   // TTS/STT 텍스트 치환 규칙
		callbackFunc: function(result) {
			// 사용자가 [Done]을 눌렀을 때 호출
			console.log(result.projectId);
			// result: { projectId, thumbnailUrl, spaceId, width, height, title, status, slideCount, savedAt }
		},
		eventFunc: function(projectId, eventName) {
			// 편집 화면 내 이벤트 발생 시 호출
			// eventName: openPreview, saveProject, openDownload,
			//            requestExportPng, requestExportMp4, exportedPng, exportedMp4,
			//            downloadPng, downloadMp4, openProjectInfo, updateProjectInfo
		},
		errorFunc: function(errorMessage) {
			// 토큰 만료 시 호출 → 새 토큰 발급 후 재시도 처리
			// errorMessage: "Token is invalid"
		}
	});
</script>
옵션 필수 설명
token /auth/access-token 응답의 token 값. 예: Qjky6mFiMkRn...
apiKey 레거시 방식(raw token) 사용 시에만 필요. 신규 방식은 생략
projectId 수정할 프로젝트 ID. 없으면 신규 생성
baseProjectId 템플릿 프로젝트 ID. 같은 스페이스이거나 public 상태여야 함
language 프로젝트 및 UI 언어. 미지정 시 기본 en
injector 데이터 주입/변형 명세. Injector 섹션 참고
dictionary TTS/STT 텍스트 치환 규칙. dictionary 섹션 참고
callbackFunc function(result) - [Done] 버튼 클릭 시 호출, 앱 설정에 Done Webhook이 지정된 경우 이 설정은 무시됩니다.
eventFunc function(projectId, eventName) - 편집 화면 내 이벤트 발생 시 호출
errorFunc function(errorMessage) - 토큰 만료 시 호출

videostewSDK.save()

편집 화면 상태를 저장합니다. 유저가 [Save] 버튼을 누른 것과 동일하므로 특별한 경우가 아니면 호출할 필요가 없습니다.

videostewSDK.save();

videostewSDK.done()

편집 내용을 저장하고 callbackFunc 또는 Done Webhook으로 결과를 전달합니다.

videostewSDK.done();

videostewSDK.cancel(force?)

편집기를 닫습니다. 저장되지 않은 내용이 있으면 확인 팝업이 표시됩니다.

videostewSDK.cancel();
// videostewSDK.cancel(true); // 강제 닫기
[중단]