> ## Documentation Index
> Fetch the complete documentation index at: https://api-docs.voicecheap.ai/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# URL에서 미디어 가져오기 (자막)

> 직접 접근 가능한 공개 HTTPS 오디오 또는 동영상 URL을 계정으로 가져옵니다. 리디렉션과 사설 네트워크는 거부되며, 파일 및 길이 제한이 적용됩니다. 생성 액션에 반환된 fileKey를 사용하세요.

직접 접근 가능한 공개 HTTPS 오디오 또는 동영상 URL을 계정으로 가져옵니다. 리디렉션과 사설 네트워크는 거부되며, 파일 및 길이 제한이 적용됩니다. 생성 액션에 반환된 fileKey를 사용하세요.

```http theme={null}
POST https://api.voicecheap.ai/v1/actions/subtitles_upload_import
```

## 인증 및 권한

<ParamField header="x-api-key" type="string" required>
  이 헤더에 VoiceCheap API 키를 전달하세요. 동일한 API 키를 사용하는 Authorization: Bearer도 지원합니다. OAuth 액세스 토큰은 MCP에서만 허용되며, 이
  REST 엔드포인트에서는 사용할 수 없습니다.
</ParamField>

필요한 권한: `subtitles:write`.

활성 유료 구독이 필요합니다. 권한은 팀 역할, 리소스 소유권, 미디어 크레딧 또는 요금제 한도를 변경하지 않습니다.

## 매개변수

<ParamField body="url" type="string" required>
  텍스트 값입니다.

  최대 길이: 4096. 형식: "uri".
</ParamField>

<ParamField body="filename" type="string">
  텍스트 값입니다.

  최소 길이: 1. 최대 길이: 255. 패턴: `^[^/\\\r\n\0]+$`.
</ParamField>

<ParamField body="kind" type="string" required>
  텍스트 값입니다.

  허용값: "transcription", "video\_to\_srt", "add\_subtitles", "animated\_captions", "project".
</ParamField>

<ParamField body="requestId" type="string">
  전송 계층에서는 선택 사항입니다. 생략하면 서버가 유효성 검사 전에 식별자를 추가합니다. 응답이 유실된 경우 안전하게 복구할 수 있도록 고정된 UUID v4를 직접 제공하세요.

  형식: "uuid". 패턴: `^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}$`.
</ParamField>

<Accordion title="전체 입력 스키마">
  아래 JSON Schema는 검색을 통해 제공되는 정확한 필드 이름, 중첩 유형, 기본값, 범위 및 허용값을 유지합니다. 추가적인 필드 간 규칙은 작업 참고 사항에 나와 있습니다.

  ```json theme={null}
  {
    "type": "object",
    "properties": {
      "url": {
        "type": "string",
        "maxLength": 4096,
        "format": "uri"
      },
      "filename": {
        "type": "string",
        "minLength": 1,
        "maxLength": 255,
        "pattern": "^[^/\\\\\\r\\n\\0]+$"
      },
      "kind": {
        "type": "string",
        "enum": ["transcription", "video_to_srt", "add_subtitles", "animated_captions", "project"]
      },
      "requestId": {
        "description": "UUID v4 for this action. Reuse the same ID with identical arguments on retries.",
        "type": "string",
        "format": "uuid",
        "pattern": "^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}$"
      }
    },
    "required": ["url", "kind"],
    "additionalProperties": false
  }
  ```
</Accordion>

## 멱등성

각 변경 작업에 대해 requestId 또는 Idempotency-Key HTTP 헤더에 UUID v4를 사용하세요. 네트워크 오류 후에는 동일한 식별자와 동일한 인수를 재사용하세요. 둘 다 제공하는 경우 값이 일치해야 합니다. 저장된 요청을 재전송해도 작업이 반복되거나 월간 호출이 추가로 차감되지 않습니다. 실패하거나 중단된 요청은 자동으로 다시 시작되지 않습니다.

첫 실행이 일반적으로 동기식인 경우에도, 재시도 시 동일한 요청이 아직 실행 중이면 모든 변경 작업에서 HTTP 202를 반환할 수 있습니다. 실행은 완료되었지만 resultStored가 false이면, 재시도 시 원래 결과 대신 저장된 요청 상태를 HTTP 200으로 반환합니다. 해당 영역의 기록, 결과 또는 다운로드 액션으로 출력을 조회하세요.

## 요청 예제

예제의 리소스 식별자와 미디어 키를 계정에서 반환된 값으로 바꾸세요. 동일한 변경 작업을 재시도할 때는 요청 식별자를 유지하세요.

<RequestExample>
  ```bash cURL theme={null}
  curl --request POST 'https://api.voicecheap.ai/v1/actions/subtitles_upload_import' \
    --header "x-api-key: $VOICECHEAP_API_KEY" \
    --header 'Content-Type: application/json' \
    --data '{"url":"https://media.example.com/interview.mp4","filename":"interview.mp4","kind":"video_to_srt","requestId":"13579bdf-2468-4ace-8bdf-0123456789ab"}'
  ```

  ```javascript JavaScript theme={null}
  const input = {
    url: 'https://media.example.com/interview.mp4',
    filename: 'interview.mp4',
    kind: 'video_to_srt',
    requestId: '13579bdf-2468-4ace-8bdf-0123456789ab',
  };
  const response = await fetch('https://api.voicecheap.ai/v1/actions/subtitles_upload_import', {
    method: 'POST',
    headers: {
      'x-api-key': process.env.VOICECHEAP_API_KEY,
      'Content-Type': 'application/json',
    },
    body: JSON.stringify(input),
  });
  const body = await response.json();
  if (!response.ok) throw new Error(body.code + ': ' + body.message);
  console.log(body);
  ```

  ```python Python theme={null}
  import os
  import requests

  response = requests.post(
      "https://api.voicecheap.ai/v1/actions/subtitles_upload_import",
      headers={"x-api-key": os.environ["VOICECHEAP_API_KEY"]},
      json={"url": "https://media.example.com/interview.mp4", "filename": "interview.mp4", "kind": "video_to_srt", "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab"},
      timeout=120,
  )
  body = response.json()
  if not response.ok:
      raise RuntimeError(f"{body.get('code')}: {body.get('message')}")
  print(body)
  ```
</RequestExample>

## 응답

이 작업은 실행 중에 HTTP 202를 반환합니다. requestId를 저장하고 해당 식별자와 원래 작업 이름으로 action\_request\_get을 폴링하세요. 폴링 상태는 running, completed, failed, interrupted입니다. 완료된 결과가 별도의 미디어 작업을 가리킬 수 있으므로 해당 작업의 상태 또는 출력 액션을 이어서 사용하세요.

가져온 액터 소유 미디어 참조이며, 크기, 길이, 미디어 종류 및 읽기 URL이 검증되었습니다. 폴링 후 반환되는 완료된 액션 출력입니다.

<ResponseExample>
  ```json HTTP 202 theme={null}
  {
    "data": {
      "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab",
      "status": "running",
      "pollAction": "action_request_get",
      "pollAfterSeconds": 5
    },
    "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab"
  }
  ```

  ```json HTTP 200 theme={null}
  {
    "data": {
      "fileKey": "uploads/account-user/a1b2c3d4-e5f6-4789-8abc-def012345678-interview.mp4",
      "fileName": "interview.mp4",
      "fileSize": 1048576,
      "durationSeconds": 60,
      "mimeType": "video/mp4",
      "uploadType": "video",
      "readUrl": "https://media.example.com/uploads/account-user/a1b2c3d4-e5f6-4789-8abc-def012345678-interview.mp4"
    },
    "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab"
  }
  ```

  ```json HTTP 202 replay_running theme={null}
  {
    "data": {
      "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab",
      "operation": "subtitles_upload_import",
      "createdAt": 1792144800000,
      "updatedAt": 1792144820000,
      "status": "running",
      "pollAfterSeconds": 5
    },
    "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab"
  }
  ```

  ```json HTTP 200 replay_completed_without_result theme={null}
  {
    "data": {
      "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab",
      "operation": "subtitles_upload_import",
      "createdAt": 1792144800000,
      "updatedAt": 1792144820000,
      "status": "completed",
      "resultStored": false,
      "message": "The action completed. Retrieve its output from the corresponding history or resource action."
    },
    "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab"
  }
  ```
</ResponseExample>

## 결과 필드

| 필드 | 설명 |
| - | - |
| `data.fileKey` | 생성 액션에 사용할 소유권이 확인된 완료된 참조입니다. |
| `data.fileName` | 안전하게 정리된 가져오기 파일명입니다. |
| `data.fileSize` | 다운로드한 원본 바이트입니다. |
| `data.durationSeconds` | 미디어 분석으로 확인한 원본 길이이며, 단위는 초입니다. |
| `data.mimeType` | 지원되는 파일명 확장자에서 추론한 미디어 MIME 유형입니다. |
| `data.uploadType` | audio 또는 video입니다. |
| `data.readUrl` | 가져온 원본을 읽기 위한 임시 URL입니다. 생성에는 fileKey를 사용합니다. |

## 이 요청 복구 및 폴링

연결이 끊어진 후에도 동일한 식별자를 사용하세요. resultStored가 false이면 해당 기록, 결과 또는 다운로드 액션을 통해 출력을 조회하세요. 진행 상황을 확인하기 위해 두 번째 생성을 시작하지 마세요.

```bash theme={null}
curl --request POST 'https://api.voicecheap.ai/v1/actions/action_request_get' \
  --header "x-api-key: $VOICECHEAP_API_KEY" \
  --header 'Content-Type: application/json' \
  --data '{"requestId":"13579bdf-2468-4ace-8bdf-0123456789ab","operation":"subtitles_upload_import"}'
```

```json HTTP 200 theme={null}
{
  "data": {
    "requestId": "13579bdf-2468-4ace-8bdf-0123456789ab",
    "operation": "subtitles_upload_import",
    "status": "completed",
    "createdAt": 1792144800000,
    "updatedAt": 1792144820000,
    "resultStored": true,
    "result": {
      "fileKey": "uploads/account-user/a1b2c3d4-e5f6-4789-8abc-def012345678-interview.mp4",
      "fileName": "interview.mp4",
      "fileSize": 1048576,
      "durationSeconds": 60,
      "mimeType": "video/mp4",
      "uploadType": "video",
      "readUrl": "https://media.example.com/uploads/account-user/a1b2c3d4-e5f6-4789-8abc-def012345678-interview.mp4"
    }
  }
}
```

## 작업 참고 사항

* 유료 구독과 해당 액션 권한이 필요합니다. 실행 시 실행 주체의 개인 도구 요금제를 다시 확인합니다. 인증 정보가 팀과 연결되어 있어도 저장된 도구와 업로드 참조는 해당 실행 주체에 속합니다.
* 성공한 액션은 공유 월간 API/MCP 호출 1회를 사용합니다. 월간 호출 허용량은 Beginner 500회, Starter 5,000회, Creator 25,000회이며, Pro, Scale 및 Enterprise에는 월간 상한이 없습니다. 분당 한도는 각각 30, 60, 120, 180, 300 및 600회로 계속 적용됩니다. 도구 생성 허용량은 별도입니다.
* UUID v4 requestId 또는 동일한 Idempotency-Key 헤더를 사용하고, 다시 시도할 때 동일한 액션, ID 및 인수를 유지하세요. 캐시된 결과를 다시 반환할 때는 월간 호출 횟수를 추가로 사용하지 않습니다.
* 업로드 접두사에 따라 필요한 권한이 선택됩니다. tools는 transcription:write, subtitles는 subtitles:write, projects는 projects:write, voices는 voices:write를 사용합니다.
* 도구, 자막 및 프로젝트에서 kind는 transcription, video\_to\_srt, add\_subtitles, animated\_captions 또는 project를 허용합니다. 선택한 kind가 워크플로 제한을 결정하며 접두사가 kind를 강제하지 않습니다.
* 선택한 kind에 따라 개별 제한이 적용됩니다. transcription은 200 MiB, video\_to\_srt와 add\_subtitles는 300 MiB, animated\_captions는 250 MiB이며 오디오만 허용합니다. project에는 요금제 업로드 한도가 적용됩니다(Beginner 5 GiB, Starter 10 GiB, Creator 20 GiB, Pro 30 GiB, Scale 40 GiB, Enterprise 60 GiB). 독립형 미디어는 최대 2시간입니다. 캡션은 Beginner에서 30분, 그보다 높은 공개 요금제에서 60분까지 허용하며, 여기에 컨테이너 허용 오차 2초가 추가됩니다. 프로젝트 길이는 최대 2시간이며 Enterprise에서는 3시간입니다.
* 이 액션은 비동기로 실행됩니다. 결과에서 fileKey를 가져오기 전에 작업 이름과 원래 requestId로 action\_request\_get을 완료될 때까지 폴링하세요.
* 공개 HTTPS 오디오/동영상 파일의 직접 URL을 사용하세요. 리디렉션, 자격 증명, 프래그먼트, 443 이외의 포트 및 비공개 DNS 주소는 거부됩니다. YouTube 시청 페이지는 직접 미디어 URL이 아닙니다. 전용 YouTube 액션을 사용하세요.
* URL 경로가 지원되는 미디어 파일명으로 끝나면 filename은 선택 사항입니다. 저장되는 파일명은 안전하게 정리됩니다. 서버는 fileKey를 반환하기 전에 실제 길이를 미디어 분석으로 확인합니다.
* 가져오기는 미디어를 준비하고 성공한 월간 통합 호출 1회를 소모합니다. 일일 도구 생성 허용량은 후속 생성에서만 소모됩니다.

## 사용량

성공한 호출마다 월간 API/MCP 호출 1회가 차감됩니다. 미디어 크레딧과 해당 작업의 생성 허용량도 적용됩니다.

## 오류

| HTTP 상태 | 코드 | 의미 또는 복구 방법 |
| - | - | - |
| 400 | `CREDENTIAL_IN_QUERY` | 자격 증명이 access\_token 또는 api\_key 쿼리 매개변수로 제공되었습니다. 자격 증명은 헤더로 보내세요. |
| 400 | `EMPTY_MEDIA` | 직접 미디어 URL이 빈 본문을 반환했습니다. |
| 400 | `FILE_TOO_LARGE` | 선언된 원본 또는 다운로드한 원본이 선택한 kind의 업로드 한도를 초과합니다. |
| 400 | `IDEMPOTENCY_CONFLICT` | 헤더와 본문의 요청 ID가 다릅니다. |
| 400 | `INVALID_FILE_TYPE` | 제공된 파일명 또는 URL에서 추출한 파일명에 선택한 kind가 지원하는 확장자가 없습니다. |
| 400 | `INVALID_MEDIA_DURATION` | 다운로드한 미디어의 길이를 확인할 수 없거나 선택한 유형의 요금제 한도를 초과합니다. |
| 400 | `INVALID_MEDIA_TYPE` | 응답 콘텐츠 유형이 audio, video, application/ogg 또는 application/octet-stream이 아닙니다. |
| 400 | `INVALID_MEDIA_URL` | 사용자 자격 증명, 프래그먼트 또는 443 이외의 포트가 없는 직접 HTTPS URL을 사용하고, 유효한 미디어 파일명을 제공하세요. |
| 400 | `INVALID_REQUEST_ID` | requestId 또는 Idempotency-Key가 UUID v4가 아닙니다. |
| 400 | `MEDIA_DOWNLOAD_REFUSED` | 직접 다운로드가 HTTP 200을 반환하지 않았습니다. 리디렉션은 거부됩니다. |
| 400 | `MEDIA_IMPORT_FAILED` | 원본을 다운로드하거나, 미디어 정보를 분석하거나, 저장할 수 없습니다. 공개 URL과 미디어 형식을 확인하세요. |
| 400 | `MEDIA_URL_NOT_PUBLIC` | 호스트 이름의 주소를 확인할 수 없거나, 확인된 주소 중 하나 이상이 사설 주소 또는 그 밖의 공개되지 않은 주소입니다. |
| 400 | `VALIDATION_ERROR` | 인수가 액션 스키마를 충족하지 않거나 알 수 없는 인수가 제공되었습니다. |
| 401 | `API_KEY_EXPIRED` | API 키가 만료되었습니다. |
| 401 | `INVALID_API_KEY` | 유효하고 만료되지 않은 API 키를 제공하세요. |
| 401 | `INVALID_CREDENTIAL` | Authorization 헤더의 형식이 잘못되었거나 x-api-key와 충돌합니다. |
| 401 | `MISSING_CREDENTIAL` | 사용 가능한 헤더 자격 증명이 전달되지 않았거나 4096자를 초과했습니다. |
| 401 | `USER_NOT_FOUND` | 이 자격 증명에 연결된 계정이 더 이상 존재하지 않습니다. |
| 403 | `ACCOUNT_UNAVAILABLE` | 작업을 수행하는 계정 또는 결제 계정을 사용할 수 없거나 해당 계정이 삭제 중입니다. |
| 403 | `AMBIGUOUS_TEAM_API_KEY` | 이 자격 증명의 사용자가 둘 이상의 팀에 속해 있어 청구 컨텍스트가 모호합니다. |
| 403 | `INSUFFICIENT_SCOPE` | API 키 또는 MCP 연결에 필요한 액션 권한이 없습니다. |
| 403 | `INTEGRATION_PLAN_UNSUPPORTED` | 계정의 통합 한도를 확인할 수 없습니다. |
| 403 | `PAID_SUBSCRIPTION_REQUIRED` | 이 도구 액션이 실행되는 시점에 인증된 요청 주체에게 더 이상 유료 구독이 없습니다. |
| 403 | `SUBSCRIPTION_REQUIRED` | 활성 유료 구독을 사용하세요. |
| 403 | `TEAM_OWNER_NOT_FOUND` | 실제로 적용되는 팀 소유자 계정을 찾을 수 없습니다. |
| 409 | `CONCURRENT_ACTION_LIMIT_REACHED` | 이 계정에서는 이미 10개의 연동 액션이 실행 중입니다. 새 액션을 시작하기 전에 기존 요청을 폴링하세요. |
| 409 | `IDEMPOTENCY_CONFLICT` | 동일한 작업과 인수에 대해서만 식별자를 재사용하세요. |
| 429 | `INTEGRATION_MONTHLY_LIMIT_REACHED` | 사용된 호출과 대기 중인 호출이 공유 월간 API/MCP 허용량에 도달했습니다. |
| 429 | `INTEGRATION_RATE_LIMIT_REACHED` | 계정이 분당 통합 한도에 도달했습니다. retryAfterSeconds를 확인하세요. |
| 500 | `INTERNAL_ERROR` | 변경 작업을 재시도하기로 결정하기 전에 저장된 요청 상태와 리소스 기록을 확인하세요. |
| 503 | `ACTION_RESULT_UNAVAILABLE` | 액션이 실행되었지만 요청 결과의 영구 저장 여부를 확인하지 못했습니다. 다른 쓰기 작업을 시작하기 전에 동일한 액션과 requestId를 폴링하고 리소스 기록을 확인하세요. |
| 503 | `SERVER_RESTARTING` | 서버가 다시 시작 중입니다. 잠시 후 재시도하고, 변경 작업의 경우 동일한 요청 식별자를 유지하세요. |

```json theme={null}
{
  "code": "INSUFFICIENT_SCOPE",
  "message": "This credential does not permit the requested action.",
  "status": 403,
  "details": {
    "requiredScopes": ["subtitles:write"]
  }
}
```


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.