> This page is for 플랫폼, version V4 (default).
> For other versions, use one of these documentation indexes:
> - V4 (default): https://next.developer.frame.io/platform/v4/llms.txt
> - V4 실험적: https://next.developer.frame.io/platform/v4-experimental/llms.txt
> - 레거시: https://next.developer.frame.io/platform/v2/llms.txt

> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://next.developer.frame.io/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://next.developer.frame.io/_mcp/server.

# 미디어 링크

Frame.io는 이미지, 비디오, PDF 등 귀하의 프로젝트에 업로드된 파일들을 저장하고 처리합니다. API를 통해 파일을 가져올 때 기본 응답에는 파일 이름, 상태, 그리고 Frame.io 앱에서 열어보기 위한 `view_url`과 같은 핵심 메타데이터가 포함됩니다. 원본, 미리 보기 또는 다른 품질의 렌디션과 같은 실제 파일 콘텐츠에 액세스하려면 **include**를 사용합니다. 이 가이드에서는 **파일 나열** 및 **파일 가져오기** 엔드포인트에서 사용할 수 있는 미디어 링크 include와 각각 반환하는 내용, 그리고 사용 시기에 대해 설명합니다.

## include란 무엇인가요?

include는 파일 응답과 함께 요청할 수 있는 선택적인 필드입니다. 기본적으로 API는 이름, 상태, 유형, 타임스탬프, `view_url`과 같은 핵심 파일 메타데이터만 반환합니다. include를 사용하면 추가 데이터를 선택적으로 받아볼 수 있어, 모든 정보가 필요하지 않을 때 응답을 가볍게 유지할 수 있습니다.

### include 추가 방법

**파일 가져오기** 또는 **파일 나열** 요청에 `include` 쿼리 매개변수로 쉼표로 구분된 include 이름 목록을 전달합니다.

**`단일 include`**

```bash title="단일 include"
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.thumbnail
```

**`다중 include`**

```bash title="다중 include"
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.thumbnail,media_links.original
```

**`파일 나열에서의 include`**

```bash title="파일 나열에서의 include"
GET /v4/accounts/{account_id}/folders/{folder_id}/files?include=media_links.thumbnail
```

include는 단일 파일 가져오기 엔드포인트와 목록 나열 엔드포인트 모두에서 동일한 방식으로 작동합니다. 파일 나열에 사용할 경우, 응답에 포함된 모든 파일에 대해 include가 적용됩니다.

### SDK 예시

**`Python SDK`**

```python title="Python SDK"
import frameio

client = frameio.Frameio(auth="<YOUR_TOKEN>")

file = client.files.get(
    file_id="93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    include=["media_links.thumbnail", "media_links.original"]
)

print(file.media_links.thumbnail.url)
```

**`TypeScript SDK`**

```typescript title="TypeScript SDK"
import Frameio from "frameio";

const client = new Frameio({ auth: "<YOUR_TOKEN>" });

const file = await client.files.get("93e4079d-0a8a-4bf3-96cd-e6a03c465e5e", {
  include: ["media_links.thumbnail", "media_links.original"],
});

console.log(file.media_links?.thumbnail?.url);
```

요청하지 않은 include는 응답에서 완전히 생략됩니다.

## 미디어 링크 include 개요

#### media\_links.original

업로드된 그대로의 원본 파일

#### media\_links.thumbnail

표시 목적을 위한 PNG 미리 보기 이미지

#### media\_links.high\_quality

사용 가능한 최상의 화질로 처리된 렌디션

#### media\_links.efficient

저대역폭 사용 사례를 위해 사용 가능한 가장 작은 렌디션

#### media\_links.video\_h264\_180

스트리밍 및 재생을 위한 저해상도 180p H264 비디오 트랜스코드

#### media\_links.scrub\_sheet

스크러빙 UI 구축을 위한 비디오 프레임 썸네일 WebP 스프라이트 시트

## media\_links.original

어떠한 처리나 변환도 거치지 않고 **업로드된 그대로의 원본 파일**을 가리키는 서명된 URL을 반환합니다.

### 필드

| 필드             | 문자        | 설명   |                                                                                           |
| -------------- | --------- | ---- | ----------------------------------------------------------------------------------------- |
| `download_url` | string \\ | null | 파일 다운로드를 강제하는 서명된 URL(`Content-Disposition: attachment`)(Content-Disposition: attachment) |
| `inline_url`   | string \\ | null | 브라우저에서 직접 파일을 여는 서명된 URL(`Content-Disposition: inline; filename=<name></name>`)           |

### 사용 시기

사용자에게 원본 MOV, MP4, MXF, AVI, PSD, PNG 또는 TIFF를 다운로드하게 하거나, 다른 시스템에 원본 바이트를 전달하는 등 소스 파일이 필요할 때 `media_links.original`을 사용합니다.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.original
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "hero-banner.png",
    "type": "file",
    "media_links": {
      "original": {
        "download_url": "https://s3.amazonaws.com/...",
        "inline_url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

> **Warning**
>
> 이 URL들은 **임시로 서명된 S3 URL**이므로 만료됩니다. 이를 캐시하거나 저장하지 마시고, 필요할 때마다 새로운 URL을 요청하세요.

## media\_links.thumbnail

에셋의 **PNG 미리 보기 이미지**를 반환하며, 높이는 540px로 제한됩니다. 이는 원본 파일이 아닌 처리된 렌디션이며, 계정 설정에 따라 워터마크가 적용될 수 있습니다.

### 필드

| 필드             | 문자        | 설명   |                                                         |
| -------------- | --------- | ---- | ------------------------------------------------------- |
| `download_url` | string \\ | null | PNG 썸네일 다운로드를 강제하는 서명된 URL                              |
| `url`          | string \\ | null | `Content-Disposition` 헤더 없이 PNG 썸네일을 인라인으로 제공하는 서명된 URL |

### 사용 시기

그리드 뷰, 갤러리 또는 파일 피커와 같이 에셋의 **시각적 미리 보기**를 표시해야 할 때 `media_links.thumbnail`을 사용합니다. 원본보다 빠르게 로드되며 항상 웹에서 안전하게 사용할 수 있는 PNG 형식입니다.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.thumbnail
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "hero-banner.png",
    "type": "file",
    "media_links": {
      "thumbnail": {
        "download_url": "https://s3.amazonaws.com/...",
        "url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

## media\_links.high\_quality

**사용 가능한 최상의 화질로 처리된 에셋 렌디션**의 다운로드 URL을 반환합니다. Frame.io는 최대 2160p까지 해상도를 단계별로 높여가며 업로드를 처리합니다. API는 **요청 시점에** 사용 가능한 가장 높은 렌디션을 반환합니다. 따라서 요청할 때 540p 렌디션만 처리가 완료된 상태라면, 더 높은 렌디션이 준비될 때까지 API는 540p를 반환합니다.

### 필드

| 필드             | 문자        | 설명   |                                  |
| -------------- | --------- | ---- | -------------------------------- |
| `download_url` | string \\ | null | 요청 시점에 사용 가능한 최고 화질 렌디션의 서명된 URL |

### 사용 시기

다운스트림 처리를 위해 고해상도 렌디션을 내보내거나 전체 해상도 미리 보기를 제공하는 등 **원본 파일 없이 최고의 화질 버전**을 원할 때 `media_links.high_quality`를 사용합니다. 최고의 화질이 필요하다면 파일의 `status` 필드를 확인하고, 파일 처리가 완료되어(`ready`) 전체 해상도의 렌디션이 모두 처리된 후에 이 include를 요청하세요.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.high_quality
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "hero-banner.png",
    "type": "file",
    "media_links": {
      "high_quality": {
        "download_url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

## media\_links.efficient

**사용 가능한 처리된 렌디션 중 가장 작은 용량**의 다운로드 URL을 반환합니다. 이는 `high_quality`와 반대로, Frame.io가 사용 가능한 가장 낮은 해상도의 렌디션을 선택합니다.

### 필드

| 필드             | 문자        | 설명   |                               |
| -------------- | --------- | ---- | ----------------------------- |
| `download_url` | string \\ | null | 가장 작고 가장 효율적인 렌디션을 위한 서명된 URL |

### 사용 시기

저대역폭 환경에서 빠른 미리 보기를 생성하거나 전체 해상도가 필요 없는 썸네일 파이프라인에 제공하는 등, **품질보다 대역폭이나 파일 크기가 더 중요**할 때 `media_links.efficient`를 사용합니다.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.efficient
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "hero-banner.png",
    "type": "file",
    "media_links": {
      "efficient": {
        "download_url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

## media\_links.video\_h264\_180

에셋의 **저해상도 180p H264 비디오 트랜스코드**에 대한 스트리밍 및 다운로드 URL을 반환합니다.

> **Warning**
>
> 이는 이전 include입니다. 해당 에셋에 대해 180p 트랜스코드가 생성되지 않은 경우 `null`을 반환합니다. 특정 트랜스코드가 존재한다고 가정하기보다는, 사용 가능한 최적의 저화질 렌디션을 선택해 주는 `media_links.efficient`를 대부분의 사용 사례에서 권장합니다.

### 필드

| 필드             | 문자        | 설명   |                                  |
| -------------- | --------- | ---- | -------------------------------- |
| `download_url` | string \\ | null | 180p H264 비디오를 다운로드하기 위한 서명된 URL |
| `url`          | string \\ | null | 180p H264 비디오 스트리밍을 위한 서명된 URL   |

### 사용 시기

정확히 180p H264 형식을 요구하는 기존 플레이어 또는 파이프라인과 연동하는 등 반드시 180p H264 트랜스코드가 필요할 때만 `media_links.video_h264_180`을 사용합니다. 특정 에셋에 대해 이 트랜스코드가 존재하지 않으면 두 URL 모두 `null`이 됩니다.

> **Warning**
>
> video\_h264\_180 파일에는 오디오가 포함되어 있지 않습니다. 이 파일은 필요할 때 매우 효율적인 미리 보기용으로 사용하도록 고안되었습니다.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.video_h264_180
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "interview-clip.mp4",
    "type": "file",
    "media_links": {
      "video_h264_180": {
        "download_url": "https://s3.amazonaws.com/...",
        "url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

## media\_links.scrub\_sheet

**WebP 스프라이트 시트**(비디오 재생 시간 동안 균일하게 샘플링된 비디오 프레임 썸네일 그리드가 포함된 단일 이미지)를 반환합니다. 이는 사용자가 타임라인을 드래그할 때 플레이어에 미리 보기 프레임을 보여주는 비디오 스크러빙 UI를 구축하는 데 사용됩니다.

> **Info**
>
> 스크럽 시트는 **비디오 에셋에 대해서만** 생성됩니다. 이미지, PDF 및 기타 비디오가 아닌 파일에 대해서는 이 include 요청 시 `null` URL이 반환됩니다.

### 필드

| 필드                 | 문자        | 설명                |                                          |
| ------------------ | --------- | ----------------- | ---------------------------------------- |
| `download_url`     | string \\ | null              | WebP 스프라이트 시트를 다운로드하기 위한 서명된 URL         |
| `url`              | string \\ | null              | WebP 스프라이트 시트를 인라인으로 로드하기 위한 서명된 URL     |
| `metadata`         | object \\ | null              | 개별 프레임 추출을 위한 타일 레이아웃 정보(실험적인 API에서만 제공) |
| **`metadata` 필드:** |           |                   |                                          |
| 필드                 | 문자        | 설명                |                                          |
| ---                | ---       | ---               |                                          |
| `tile_x`           | integer   | 그리드의 썸네일 열 개수     |                                          |
| `tile_y`           | integer   | 그리드의 썸네일 행 개수     |                                          |
| `thumb_width`      | integer   | 각 썸네일의 너비(픽셀)     |                                          |
| `thumb_height`     | integer   | 각 썸네일의 높이(픽셀)     |                                          |
| `padding`          | integer   | 썸네일 사이의 간격(픽셀)    |                                          |
| `frames`           | integer   | 시트에서 샘플링된 총 프레임 수 |                                          |

### 사용 시기

사용자가 스크러빙할 때 미리 보기 썸네일을 표시해야 하는 사용자 지정 비디오 플레이어 또는 타임라인 UI를 구축할 때 `media_links.scrub_sheet`를 사용합니다. 각 프레임에 대해 개별적인 요청을 보내는 대신, 스프라이트 시트는 모든 미리 보기 프레임을 단일 이미지 다운로드로 묶어 제공합니다.

### 요청 예시

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.scrub_sheet
```

### 응답 예시

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "interview-clip.mp4",
    "type": "file",
    "media_links": {
      "scrub_sheet": {
        "download_url": "https://assets.frame.io/...",
        "url": "https://assets.frame.io/...",
        "metadata": {
          "tile_x": 10,
          "tile_y": 10,
          "thumb_width": 160,
          "thumb_height": 90,
          "padding": 1,
          "frames": 100
        }
      }
    }
  }
}
```

### 스프라이트 시트에서 프레임 추출하기

스프라이트 시트는 `tile_x`(열) × `tile_y`(행)의 그리드로 구성됩니다. 특정 프레임 인덱스(0부터 시작)의 썸네일을 표시하려면 이미지 내에서의 위치를 계산하세요.

```javascript
function getFrameOffset(frameIndex, metadata) {
  const { tile_x, thumb_width, thumb_height, padding } = metadata;

  const col = frameIndex % tile_x;
  const row = Math.floor(frameIndex / tile_x);

  return {
    x: col * (thumb_width + padding),
    y: row * (thumb_height + padding),
    width: thumb_width,
    height: thumb_height,
  };
}
```

그런 다음 CSS의 `background-position`을 사용하여 스프라이트 시트에서 올바른 타일을 표시할 수 있습니다.

```javascript
function applyFrameToElement(el, frameIndex, scrubSheet) {
  const { x, y, width, height } = getFrameOffset(frameIndex, scrubSheet.metadata);

  el.style.backgroundImage = `url(${scrubSheet.url})`;
  el.style.backgroundPosition = `-${x}px -${y}px`;
  el.style.width = `${width}px`;
  el.style.height = `${height}px`;
}
```

재생 위치(초 단위)를 프레임 인덱스에 매핑하려면, 총 비디오 재생 시간과 시트의 프레임 수를 사용하세요.

```javascript
function positionToFrameIndex(currentSeconds, durationSeconds, metadata) {
  const progress = currentSeconds / durationSeconds;
  return Math.min(
    Math.floor(progress * metadata.frames),
    metadata.frames - 1
  );
}
```

> **Info**
>
> `metadata` 필드는 실험적인 API 버전에서만 사용할 수 있습니다. 안정화된 V4 API에서 `scrub_sheet`는 `download_url`과 `url`만 반환합니다.

## 여러 개의 include 결합하기

단일 API 호출에서 여러 include를 한 번에 요청할 수 있습니다.

```bash
GET /v4/accounts/{account_id}/files/{file_id}?include=media_links.thumbnail,media_links.original
```

```json
{
  "data": {
    "id": "93e4079d-0a8a-4bf3-96cd-e6a03c465e5e",
    "name": "hero-banner.png",
    "type": "file",
    "media_links": {
      "thumbnail": {
        "download_url": "https://s3.amazonaws.com/...",
        "url": "https://s3.amazonaws.com/..."
      },
      "original": {
        "download_url": "https://s3.amazonaws.com/...",
        "inline_url": "https://s3.amazonaws.com/..."
      }
    }
  }
}
```

## 상황에 맞는 include 선택

| 목표                            | 사용할 include                           |
| ----------------------------- | ------------------------------------- |
| UI에 미리 보기 이미지 표시              | `media_links.thumbnail`               |
| 사용자가 원본 파일을 다운로드할 수 있도록 허용    | `media_links.original`                |
| 브라우저에서 직접 원본 파일 열기            | `media_links.original` → `inline_url` |
| 내보내기를 위한 최고 화질의 렌디션 가져오기      | `media_links.high_quality`            |
| 저대역폭 사용을 위한 작은 렌디션 가져오기       | `media_links.efficient`               |
| 저해상도 비디오의 스트리밍 또는 다운로드(이전)    | `media_links.video_h264_180`          |
| 프레임 미리 보기가 포함된 비디오 스크러빙 UI 구축 | `media_links.scrub_sheet`             |
| 사용자를 Frame.io의 해당 파일로 이동시키기   | 기본 파일 응답에서 `view_url`을 사용하세요.         |

> **Info**
>
> include를 사용하지 않아도 모든 파일 응답에서 제공되는 `view_url`은 Frame.io 웹 앱으로 바로 연결되는 영구적인 딥 링크입니다. 이는 미디어 URL이 **아니며**, Frame.io UI를 열고 만료 기한이 없습니다. 프로그래밍 방식으로 파일을 제공하거나 다운로드해야 할 때가 아니라, 사용자가 Frame.io에서 직접 에셋을 리뷰하거나 코멘트를 작성하도록 안내하고자 할 때 이 URL을 사용하세요.

## include 가용성

미디어 링크 include는 Frame.io가 업로드된 파일의 처리를 완료한 후에만 정보가 채워집니다. 업로드 직후에 include를 요청하면, 트랜스코딩이 진행되는 동안 URL이 `null`로 표시될 수 있습니다. 파일 오브젝트의 `status` 필드를 확인하세요. 상태가 `ready`가 되면 include를 사용할 수 있습니다.