트랜스코딩 입문: FFmpeg, ABR Ladder, NVENC, Quick Sync, CMAF까지 한 번에 이해하기

들어가며: 왜 트랜스코딩을 공부하게 되었나
처음에는 트랜스코딩을 단순히 “영상 파일을 다른 형식으로 바꾸는 작업” 정도로 생각했다.
예를 들어 .mov 파일을 .mp4로 바꾸거나, 용량이 큰 영상을 더 작게 압축하는 일이 트랜스코딩이라고 막연히 이해하고 있었다. 그런데 스트리밍 구조를 조금 더 들여다보니 생각보다 훨씬 많은 질문이 따라왔다.
- 왜 같은 영상을 1080p, 720p, 480p처럼 여러 개로 만들어야 할까?
- FFmpeg는 정확히 어느 단계에서 쓰이는 도구일까?
- NVENC나 Quick Sync 같은 하드웨어 인코딩은 CPU 인코딩보다 무조건 좋은 걸까?
- CMAF는 코덱일까, 컨테이너일까, 아니면 스트리밍 방식일까?
- 실제 프로젝트에서는 화질, 용량, 속도, 호환성 중 무엇을 기준으로 선택해야 할까?
이 글은 위 질문에서 출발해 트랜스코딩의 큰 그림을 정리한 학습 기록이다. 단순히 용어를 외우는 방식이 아니라, “왜 필요한지 → 어떻게 동작하는지 → 실제 프로젝트에서는 어떻게 판단할 수 있는지” 흐름으로 정리해보려고 한다.
이 글에서 다룰 질문들
이 글에서는 다음 질문을 중심으로 트랜스코딩을 살펴본다.
- 트랜스코딩은 단순히 영상 파일을 변환하는 작업일까?
- 스트리밍 서비스에서 ABR ladder는 왜 필요할까?
- FFmpeg는 트랜스코딩 파이프라인에서 어떤 역할을 할까?
- NVENC와 Quick Sync 같은 하드웨어 인코딩은 언제 유리할까?
- CMAF는 HLS, DASH와 어떤 관계가 있을까?
- 실제 프로젝트에서는 어떤 기준으로 인코딩 방식을 선택해야 할까?
먼저 배경부터 이해하기
영상 스트리밍을 택배 배송에 비유해보면 이해가 쉽다.
하나의 고화질 원본 영상은 매우 큰 택배 상자와 같다. 집 앞까지 고속도로가 잘 깔려 있고, 받는 사람이 큰 상자를 처리할 수 있다면 그대로 보내도 된다. 하지만 현실은 다르다.
누군가는 빠른 Wi-Fi 환경에서 최신 스마트폰으로 영상을 본다. 또 다른 누군가는 지하철에서 불안정한 LTE 환경으로 영상을 본다. 어떤 사용자는 TV에서 4K 영상을 보고, 어떤 사용자는 오래된 브라우저에서 480p 영상만 안정적으로 재생할 수 있다.
즉, 같은 영상을 모든 사용자에게 똑같이 보내는 것은 비효율적이다.
그래서 원본 영상을 여러 환경에 맞게 다시 가공한다. 이 과정에서 해상도를 낮추기도 하고, bitrate를 조정하기도 하고, 코덱을 바꾸기도 하며, 스트리밍에 적합한 조각 파일로 나누기도 한다.
이때 등장하는 핵심 개념이 바로 트랜스코딩이다.
기본 용어 정리
트랜스코딩을 이해하려면 비슷하게 생긴 용어들을 먼저 구분해야 한다.
| 용어 | 의미 | 예시 | 화질 손실 |
|---|---|---|---|
| Remux | 코덱은 그대로 두고 컨테이너만 변경 | MKV → MP4 | 거의 없음 |
| Transmux | 스트리밍 형식에 맞게 포장만 변경 | MP4 → HLS segment | 보통 없음 |
| Transcode | 디코딩 후 다시 인코딩 | H.264 → H.265 | 있음 |
| Transrate | 해상도는 유지하고 bitrate 변경 | 1080p 8Mbps → 1080p 4Mbps | 있음 |
| Transsize | 해상도 변경 | 1080p → 720p | 있음 |
| Packaging | HLS/DASH/CMAF용 manifest와 segment 생성 | .m3u8, .mpd, .m4s 생성 | 보통 없음 |
여기서 중요한 점은 모든 변환이 트랜스코딩은 아니라는 것이다.
예를 들어 영상 코덱과 오디오 코덱은 그대로 두고 컨테이너만 바꾸는 경우에는 다시 인코딩할 필요가 없다. 이때는 FFmpeg에서 -c copy 옵션을 사용해 stream copy를 할 수 있다.
ffmpeg -i input.mkv -c copy output.mp4
위 명령어는 영상을 다시 압축하지 않고 컨테이너만 바꾸는 예시다. 이 경우 인코딩을 다시 하지 않기 때문에 속도가 빠르고 화질 손실도 거의 없다.
반대로 해상도, bitrate, 코덱, 프레임 구조 등을 바꿔야 한다면 디코딩 후 다시 인코딩해야 한다. 이때가 일반적으로 말하는 트랜스코딩에 가깝다.
전체 구조 한눈에 보기

트랜스코딩 파이프라인은 크게 보면 다음 흐름으로 동작한다.
원본 영상
↓
입력 분석
↓
디코딩
↓
필터 처리
- 해상도 변경
- 색상 변환
- 자막 처리
- 오디오 처리
↓
인코딩
- H.264
- H.265/HEVC
- AV1
↓
패키징
- HLS
- DASH
- CMAF
↓
CDN / Storage
↓
Player
여기서 FFmpeg는 입력 분석, 디코딩, 필터링, 인코딩, 패키징까지 넓은 범위를 처리할 수 있다. 그래서 미디어 파이프라인을 공부할 때 FFmpeg는 거의 필수 도구처럼 등장한다.
다만 실제 서비스에서는 FFmpeg 하나로 모든 것을 끝내기보다, 인코딩 작업과 패키징 작업을 분리하거나, 병렬 작업 큐를 구성하거나, 품질 측정과 모니터링을 별도로 붙이는 경우가 많다.
핵심 개념 1: 트랜스코딩은 왜 필요한가
트랜스코딩이 필요한 이유는 크게 네 가지로 정리할 수 있다.
1. 다양한 네트워크 환경 대응
사용자의 네트워크 상태는 계속 변한다.
처음에는 Wi-Fi로 영상을 보다가 지하철로 이동하면서 LTE로 바뀔 수 있고, 순간적으로 네트워크 품질이 떨어질 수도 있다. 이때 하나의 고화질 파일만 제공하면 버퍼링이 자주 발생한다.
이를 해결하기 위해 같은 영상을 여러 품질 단계로 만들어 둔다.
예를 들어 다음과 같은 방식이다.
| 품질 단계 | 해상도 | 대략적인 video bitrate |
|---|---|---|
| High | 1920x1080 | 5,000kbps |
| Medium | 1280x720 | 2,800kbps |
| Low | 854x480 | 1,400kbps |
| Very Low | 640x360 | 800kbps |
플레이어는 네트워크 상태가 좋을 때는 1080p 영상을 재생하고, 네트워크가 불안정해지면 720p 또는 480p로 전환한다.
이런 방식을 ABR, 즉 Adaptive Bitrate Streaming이라고 부른다.
2. 다양한 디바이스 호환성 확보
모든 디바이스가 모든 코덱을 잘 재생하는 것은 아니다.
최신 기기는 H.265/HEVC나 AV1을 지원할 수 있지만, 오래된 브라우저나 저사양 디바이스에서는 H.264가 더 안전한 선택일 수 있다. 특히 웹, 모바일, TV, 셋톱박스까지 모두 지원해야 하는 서비스라면 코덱 선택은 단순히 압축률만 보고 결정할 수 없다.
일반적으로 호환성을 가장 넓게 가져가야 한다면 H.264 + AAC 조합이 여전히 무난한 선택이 될 수 있다. 반면 저장 비용이나 고화질 압축 효율이 더 중요하다면 HEVC나 AV1을 검토할 수 있다.
3. 저장 비용과 전송 비용 절감
영상 서비스에서 비용은 크게 두 군데에서 발생한다.
- 저장소 비용
- 네트워크 전송 비용
원본 영상만 저장하는 것보다 여러 해상도의 결과물을 저장하면 저장소 사용량은 늘어난다. 하지만 사용자가 항상 최고화질만 보는 것은 아니기 때문에, 적절한 ABR ladder를 제공하면 전체 전송량을 줄일 수 있다.
특히 모바일 환경에서는 1080p를 무조건 보내는 것보다 720p나 480p를 선택적으로 보내는 편이 더 효율적일 수 있다.
4. 스트리밍 형식에 맞는 구조 만들기
일반적인 MP4 파일 하나를 그대로 다운로드해서 재생하는 방식과, HLS/DASH처럼 작은 조각을 순차적으로 받아 재생하는 방식은 다르다.
스트리밍에서는 영상을 일정 시간 단위의 segment로 나누고, 플레이어가 playlist 또는 manifest를 보고 필요한 segment를 가져간다.
예를 들어 HLS에서는 .m3u8 playlist가 있고, DASH에서는 .mpd manifest가 있다. CMAF를 사용하면 fragmented MP4 기반의 segment를 HLS와 DASH에서 함께 활용할 수 있는 구조를 만들 수 있다.
핵심 개념 2: ABR ladder는 무엇인가
ABR ladder는 같은 영상을 여러 품질 단계로 만든 묶음이다.
여기서 ladder는 말 그대로 사다리처럼 여러 단계를 의미한다. 사용자의 네트워크 상황과 디바이스 성능에 따라 플레이어가 적절한 단계를 오르내린다.
1080p 5000kbps ── 네트워크 좋음
720p 2800kbps
480p 1400kbps
360p 800kbps ── 네트워크 불안정

ABR ladder를 만들 때 중요한 것은 단순히 해상도와 bitrate를 많이 나열하는 것이 아니다. 각 단계가 실제로 의미 있는 품질 차이를 가져야 하고, 플레이어가 자연스럽게 전환할 수 있어야 한다.
ABR ladder에서 중요한 기준
| 기준 | 설명 |
|---|---|
| 해상도 | 1080p, 720p, 480p 등 화면 크기 |
| bitrate | 초당 전송해야 하는 데이터 양 |
| GOP 길이 | keyframe 간격 |
| segment 길이 | HLS/DASH에서 나누는 조각 길이 |
| codec profile | 디바이스 호환성과 관련 |
| audio 설정 | bitrate, channel, sample rate 등 |
여기서 특히 중요한 것이 GOP와 keyframe alignment다.
GOP는 Group of Pictures의 약자로, keyframe부터 다음 keyframe 전까지의 프레임 묶음이다. ABR 전환은 보통 keyframe 지점에서 안정적으로 이루어진다. 따라서 여러 품질 단계의 keyframe 위치가 서로 맞아야 한다.
예를 들어 30fps 영상에서 2초마다 keyframe을 넣고 싶다면 GOP 길이는 60프레임이 된다.
-g 60 -keyint_min 60 -sc_threshold 0
각 옵션의 의미는 다음과 같다.
| 옵션 | 의미 |
|---|---|
-g 60 | 최대 GOP 길이를 60프레임으로 설정 |
-keyint_min 60 | 최소 keyframe 간격을 60프레임으로 설정 |
-sc_threshold 0 | 장면 전환에 의해 임의 keyframe이 생기는 것을 억제 |
이 설정은 모든 상황에서 정답은 아니다. 하지만 ABR ladder를 실습할 때는 각 rendition의 keyframe 위치를 맞추기 위한 출발점으로 이해할 수 있다.
핵심 개념 3: FFmpeg는 어디에 쓰이는가
FFmpeg는 미디어 파일을 다루는 대표적인 CLI 도구다. 입력을 읽고, 디코딩하고, 필터를 적용하고, 다시 인코딩하고, 원하는 컨테이너나 스트리밍 형식으로 출력할 수 있다.
가장 먼저 익혀야 할 명령어는 ffprobe다.
ffprobe -hide_banner -i input.mp4
이 명령어는 입력 파일의 코덱, 해상도, duration, audio stream, pixel format 같은 정보를 확인하는 데 사용한다.
조금 더 구조화된 형태로 보고 싶다면 JSON 출력도 가능하다.
ffprobe -v error \
-show_format -show_streams \
-of json input.mp4
트랜스코딩을 시작하기 전에 원본을 분석하는 과정은 매우 중요하다. 원본이 VFR인지, 오디오가 몇 개인지, 색상 정보가 무엇인지, 자막이 포함되어 있는지에 따라 처리 방식이 달라질 수 있기 때문이다.
FFmpeg로 단일 해상도 트랜스코딩하기
가장 기본적인 예시는 720p MP4 파일을 만드는 것이다.
ffmpeg -i input.mp4 \
-vf "scale=-2:720" \
-c:v libx264 -preset slow -crf 23 \
-c:a aac -b:a 128k \
output_720p.mp4
각 옵션을 나눠서 보면 다음과 같다.
| 옵션 | 의미 |
|---|---|
-i input.mp4 | 입력 파일 지정 |
-vf "scale=-2:720" | 세로 해상도를 720으로 맞추고, 가로는 비율에 맞춰 자동 계산 |
-c:v libx264 | 비디오 코덱으로 x264 사용 |
-preset slow | 인코딩 속도보다 압축 효율을 조금 더 우선 |
-crf 23 | 품질 기반 인코딩 값 |
-c:a aac | 오디오를 AAC로 인코딩 |
-b:a 128k | 오디오 bitrate를 128kbps로 설정 |
여기서 scale=-2:720에서 -2를 사용하는 이유는 가로 해상도를 자동 계산하되 짝수로 맞추기 위해서다. H.264에서 많이 쓰는 yuv420p 같은 pixel format은 가로, 세로가 짝수인 것이 안전하다.
핵심 개념 4: Rate Control 이해하기
트랜스코딩을 공부하다 보면 CRF, CBR, VBR 같은 용어를 자주 만난다. 모두 bitrate를 어떻게 제어할지와 관련된 개념이다.
CRF
CRF는 Constant Rate Factor의 약자로, 목표 bitrate가 아니라 목표 품질을 기준으로 인코딩하는 방식이다.
ffmpeg -i input.mp4 \
-c:v libx264 -preset slow -crf 23 \
-c:a aac -b:a 128k \
output.mp4
CRF는 VOD 파일 변환에 자주 사용된다. 파일 크기를 정확히 예측하기는 어렵지만, 일정한 체감 품질을 얻기 좋다.
일반적으로 x264 기준으로는 다음처럼 이해할 수 있다.
| CRF 값 | 경향 |
|---|---|
| 18 | 높은 품질, 큰 파일 |
| 20~23 | 일반적인 균형 |
| 24~28 | 더 작은 파일, 품질 저하 가능 |
| 30 이상 | 압축이 강하고 손실이 커질 수 있음 |
단, 적절한 CRF 값은 콘텐츠 종류, 해상도, 코덱, 요구 품질에 따라 달라질 수 있다.
CBR
CBR은 Constant Bitrate의 약자로, bitrate를 일정하게 유지하려는 방식이다.
ffmpeg -i input.mp4 \
-c:v libx264 \
-b:v 3000k -maxrate 3000k -bufsize 6000k \
-c:a aac -b:a 128k \
output.mp4
라이브 스트리밍이나 네트워크 대역폭을 엄격히 제어해야 하는 상황에서 고려할 수 있다. 다만 장면 복잡도에 관계없이 bitrate를 일정하게 맞추려다 보면, 복잡한 장면에서 품질이 떨어질 수 있다.
VBR
VBR은 Variable Bitrate의 약자로, 장면 복잡도에 따라 bitrate를 유동적으로 사용하는 방식이다.
ffmpeg -i input.mp4 \
-c:v libx264 \
-b:v 3000k -maxrate 3300k -bufsize 6000k \
-c:a aac -b:a 128k \
output.mp4
ABR ladder에서는 평균 bitrate와 최대 bitrate, buffer size를 함께 조절하는 경우가 많다. 평균 bitrate만 낮춰도 순간 bitrate가 너무 크게 튀면 플레이어에서 버퍼링이 생길 수 있기 때문이다.
실제 동작 흐름 뜯어보기: HLS용 ABR ladder 만들기
이제 간단한 3단계 ABR ladder를 만든다고 가정해보자.
목표는 다음과 같다.
| 단계 | 해상도 | video bitrate | audio bitrate |
|---|---|---|---|
| 1080p | 1920x1080 | 5000k | 128k |
| 720p | 1280x720 | 2800k | 128k |
| 480p | 854x480 | 1400k | 96k |
FFmpeg로는 다음과 같은 형태로 구성할 수 있다.
mkdir -p out/1080p out/720p out/480p
ffmpeg -i input.mp4 \
-filter_complex "\
[0:v]split=3[v1080][v720][v480];\
[v1080]scale=-2:1080[v1080o];\
[v720]scale=-2:720[v720o];\
[v480]scale=-2:480[v480o]" \
-map "[v1080o]" -map 0:a:0 \
-c:v:0 libx264 -preset medium -b:v:0 5000k -maxrate:v:0 5350k -bufsize:v:0 10000k \
-g 60 -keyint_min 60 -sc_threshold 0 \
-c:a:0 aac -b:a:0 128k \
-map "[v720o]" -map 0:a:0 \
-c:v:1 libx264 -preset medium -b:v:1 2800k -maxrate:v:1 3000k -bufsize:v:1 5600k \
-g 60 -keyint_min 60 -sc_threshold 0 \
-c:a:1 aac -b:a:1 128k \
-map "[v480o]" -map 0:a:0 \
-c:v:2 libx264 -preset medium -b:v:2 1400k -maxrate:v:2 1500k -bufsize:v:2 2800k \
-g 60 -keyint_min 60 -sc_threshold 0 \
-c:a:2 aac -b:a:2 96k \
-f hls \
-hls_time 4 \
-hls_playlist_type vod \
-master_pl_name master.m3u8 \
-var_stream_map "v:0,a:0,name:1080p v:1,a:1,name:720p v:2,a:2,name:480p" \
-hls_segment_filename "out/%v/seg_%03d.ts" \
"out/%v/prog.m3u8"
위 명령어는 처음 보면 길지만, 구조를 나누면 이해하기 쉽다.
1. 입력 영상을 세 갈래로 나눈다
-filter_complex "\
[0:v]split=3[v1080][v720][v480];\
[v1080]scale=-2:1080[v1080o];\
[v720]scale=-2:720[v720o];\
[v480]scale=-2:480[v480o]"
하나의 비디오 입력을 세 개로 나눈 뒤 각각 1080p, 720p, 480p로 scale한다.
2. 각 출력 stream을 map한다
-map "[v1080o]" -map 0:a:0
1080p로 변환된 비디오와 첫 번째 오디오 stream을 하나의 출력 조합으로 매핑한다.
3. 각 rendition의 bitrate를 지정한다
-b:v:0 5000k -maxrate:v:0 5350k -bufsize:v:0 10000k
평균 bitrate, 최대 bitrate, buffer size를 지정한다. ABR에서는 순간 bitrate가 과도하게 튀지 않도록 maxrate와 bufsize를 함께 조절하는 것이 중요하다.
4. HLS playlist와 segment를 만든다
-f hls \
-hls_time 4 \
-hls_playlist_type vod \
-master_pl_name master.m3u8
HLS 형식으로 출력하고, 각 segment 길이를 4초로 설정한다. master.m3u8는 여러 품질 단계를 묶는 상위 playlist다.
CMAF는 어디에 들어가는가
HLS를 공부하다 보면 MPEG-TS segment를 많이 보게 된다. 그런데 최근 스트리밍 구조에서는 fragmented MP4 기반의 CMAF를 함께 고려하는 경우가 많다.
CMAF는 Common Media Application Format의 약자다. 이름만 보면 코덱처럼 느껴질 수 있지만, 정확히는 코덱이라기보다 스트리밍에 사용할 미디어 segment의 공통 포맷에 가깝다.

CMAF를 이해할 때 중요한 키워드는 다음 세 가지다.
| 개념 | 설명 |
|---|---|
| fMP4 | fragmented MP4. 조각난 MP4 구조 |
| init segment | 코덱 정보 등 초기화에 필요한 정보 |
| media segment | 실제 재생되는 미디어 조각 |
CMAF의 장점은 HLS와 DASH가 같은 미디어 segment를 공유할 수 있는 구조를 만들기 쉽다는 점이다.
CMAF segments
├── HLS playlist (.m3u8)
└── DASH manifest (.mpd)
즉, HLS용 segment와 DASH용 segment를 완전히 따로 만드는 대신, 공통 fMP4 segment를 만들고 HLS playlist와 DASH manifest가 이를 바라보게 할 수 있다.
FFmpeg에서 fMP4 기반 HLS를 만들고 싶다면 다음과 같이 -hls_segment_type fmp4 옵션을 사용할 수 있다.
ffmpeg -i input.mp4 \
-c:v libx264 -c:a aac \
-f hls \
-hls_time 4 \
-hls_segment_type fmp4 \
-hls_playlist_type vod \
-hls_segment_filename "out/seg_%03d.m4s" \
out/prog.m3u8
여기서 생성되는 .m4s 파일이 fragmented MP4 기반 segment다. 실제 서비스에서는 DASH manifest 생성, DRM, 저지연 스트리밍, CDN 캐싱 정책 등과 함께 더 복잡하게 설계될 수 있다.
NVENC와 Quick Sync는 언제 사용할까
트랜스코딩은 계산 비용이 큰 작업이다. 특히 여러 해상도의 ABR ladder를 동시에 만들거나, 라이브 방송을 실시간으로 처리해야 한다면 CPU만으로는 부담이 커질 수 있다.
이때 하드웨어 인코더를 활용할 수 있다.
대표적으로 NVIDIA GPU 기반의 NVENC, Intel GPU/iGPU 기반의 **Quick Sync Video(QSV)**가 있다.
| 구분 | NVENC | Quick Sync |
|---|---|---|
| 제공 주체 | NVIDIA | Intel |
| 주로 사용하는 하드웨어 | NVIDIA GPU | Intel iGPU / Intel Arc |
| FFmpeg 인코더 예시 | h264_nvenc, hevc_nvenc, av1_nvenc | h264_qsv, hevc_qsv, av1_qsv |
| 장점 | 높은 처리량, GPU 서버 활용 | 전력 효율, Intel 기반 환경에서 접근성 |
| 주의점 | GPU 세대와 드라이버 영향 | CPU/iGPU 세대와 드라이버 영향 |
| 적합한 상황 | 대량 VOD, 라이브 트랜스코딩 | 비용/전력 효율이 중요한 환경 |
NVENC 예시는 다음과 같다.
ffmpeg -hwaccel cuda -hwaccel_output_format cuda -i input.mp4 \
-vf scale_cuda=-2:720 \
-c:v h264_nvenc \
-b:v 2800k -maxrate 3000k -bufsize 5600k \
-g 60 \
-c:a aac -b:a 128k \
out_720p.mp4
각 옵션의 의미는 다음과 같다.
| 옵션 | 의미 |
|---|---|
-hwaccel cuda | CUDA 기반 하드웨어 가속 사용 |
-hwaccel_output_format cuda | 디코딩 결과를 GPU 메모리에 유지 |
scale_cuda=-2:720 | GPU에서 scale 처리 |
-c:v h264_nvenc | NVIDIA NVENC로 H.264 인코딩 |
Quick Sync 예시는 다음과 같다.
ffmpeg -i input.mp4 \
-vf scale=-2:720 \
-c:v h264_qsv \
-b:v 2800k -maxrate 3000k -bufsize 5600k \
-g 60 \
-c:a aac -b:a 128k \
out_720p.mp4

하드웨어 인코딩은 빠르다는 장점이 있다. 하지만 무조건 CPU 인코딩보다 좋은 것은 아니다.
일반적으로 같은 bitrate에서 최고 압축 효율을 목표로 한다면 libx264, libx265, SVT-AV1 같은 소프트웨어 인코더가 유리한 경우가 있다. 반대로 실시간 처리량, 비용, 지연시간이 중요하다면 NVENC나 QSV가 더 현실적인 선택이 될 수 있다.
즉, “무엇이 더 좋은가?”보다 “어떤 제약 조건에서 어떤 선택이 더 적합한가?”가 더 중요하다.
내가 헷갈렸던 부분 정리
Q1. 트랜스코딩은 단순히 영상 용량을 줄이는 작업인가?
아니다. 용량을 줄이는 것도 트랜스코딩의 목적 중 하나지만, 그것이 전부는 아니다.
트랜스코딩은 코덱 변경, 해상도 변경, bitrate 조정, 디바이스 호환성 확보, 스트리밍용 구조 생성 등과 연결된다. 특히 스트리밍 서비스에서는 사용자의 네트워크 상태에 맞춰 여러 품질 단계를 제공하기 위해 트랜스코딩이 필요하다.
다만 컨테이너만 바꾸는 작업은 트랜스코딩이 아니라 remux에 가깝다. 이 경우에는 -c copy를 사용해 재인코딩 없이 처리할 수 있다.
Q2. ABR ladder의 bitrate 값에는 정답이 있을까?
정답은 없다.
일반적인 시작점은 만들 수 있지만, 최적의 ladder는 콘텐츠 성격에 따라 달라진다. 강의 영상처럼 움직임이 적은 콘텐츠는 낮은 bitrate에서도 품질이 괜찮을 수 있다. 반면 스포츠, 게임, 콘서트처럼 움직임이 많고 장면이 복잡한 콘텐츠는 더 높은 bitrate가 필요할 수 있다.
따라서 실제 프로젝트에서는 고정 ladder를 무조건 적용하기보다, 콘텐츠 복잡도와 품질 측정 결과를 바탕으로 조정하는 것이 좋다. 더 나아가면 per-title encoding이나 content-aware encoding 같은 방식도 고려할 수 있다.
Q3. NVENC나 Quick Sync를 쓰면 항상 더 좋은가?
항상 그렇지는 않다.
하드웨어 인코딩의 가장 큰 장점은 속도와 처리량이다. 라이브 스트리밍이나 대량 VOD 처리처럼 빠르게 많은 영상을 처리해야 하는 상황에서는 매우 유리하다.
하지만 같은 bitrate에서의 압축 효율이나 세밀한 품질 조정 측면에서는 소프트웨어 인코더가 더 유리한 경우도 있다. 또한 하드웨어 인코더는 GPU 세대, 드라이버, FFmpeg 빌드 옵션에 따라 지원 기능이 달라질 수 있다.
따라서 “GPU가 있으니 무조건 NVENC”보다는 다음 기준으로 판단하는 편이 좋다.
- 실시간 처리가 필요한가?
- 동시에 처리해야 할 영상 수가 많은가?
- 저장 용량 최적화가 더 중요한가?
- 특정 코덱이나 profile이 필요한가?
- 운영 환경에서 드라이버와 하드웨어 지원이 안정적인가?
Q4. CMAF는 HLS나 DASH를 대체하는 기술인가?
정확히는 그렇지 않다.
HLS와 DASH는 플레이어가 어떤 segment를 어떤 순서로 가져올지 정의하는 스트리밍 방식에 가깝다. 반면 CMAF는 HLS와 DASH가 공통으로 사용할 수 있는 미디어 segment 형식에 가깝다.
즉, CMAF는 HLS/DASH를 대체한다기보다 함께 사용될 수 있다.
예를 들어 하나의 CMAF segment 세트를 만들고, HLS playlist와 DASH manifest가 같은 segment를 바라보는 구조를 만들 수 있다. 이 방식은 저장 효율, CDN 캐싱 효율, 저지연 스트리밍 설계 측면에서 장점이 있을 수 있다.
설계 관점에서 다시 보기
실제 프로젝트에서 트랜스코딩 파이프라인을 설계한다면 다음 질문부터 해야 한다.
- VOD인가, Live인가?
- 최고 화질이 중요한가, 처리 속도가 중요한가?
- 지원해야 하는 디바이스 범위는 어디까지인가?
- 저장 비용과 전송 비용 중 무엇이 더 민감한가?
- HLS만 지원하면 되는가, DASH까지 고려해야 하는가?
- 저지연 스트리밍이 필요한가?
- 자막, 다국어 오디오, DRM이 필요한가?
선택지를 표로 정리하면 다음과 같다.
| 선택지 | 장점 | 단점 | 적합한 상황 |
|---|---|---|---|
libx264 CPU 인코딩 | 호환성 좋음, 품질 조정 유연 | 처리 속도 부담 | VOD, 품질 중심 인코딩 |
libx265 CPU 인코딩 | H.264보다 효율적일 수 있음 | 인코딩 비용 큼, 호환성 확인 필요 | 고화질 VOD, 저장 비용 최적화 |
| NVENC | 빠른 처리, GPU 활용 | 세대/드라이버 영향, 압축 효율 확인 필요 | 라이브, 대량 트랜스코딩 |
| Quick Sync | 전력 효율, Intel 환경 활용 | 하드웨어 세대 영향 | 비용 효율적인 서버 환경 |
| HLS TS | 호환성 넓음, 오래된 구조 | DASH와 segment 공유 어려움 | 넓은 호환성이 중요한 서비스 |
| HLS fMP4/CMAF | HLS/DASH segment 공유 가능 | 플레이어/패키징 검증 필요 | 멀티 플랫폼, CDN 효율 고려 |
| 고정 ABR ladder | 설계 단순 | 콘텐츠별 최적화 부족 | 초기 MVP, 단순 서비스 |
| Per-title ladder | 콘텐츠별 최적화 가능 | 분석/자동화 필요 | 대규모 VOD 서비스 |
VOD와 Live는 판단 기준이 다르다
트랜스코딩을 공부하면서 가장 크게 느낀 점은 VOD와 Live의 목표가 다르다는 것이다.
VOD
VOD는 이미 업로드된 영상을 처리한다. 실시간성이 상대적으로 덜 중요하기 때문에 더 느린 preset을 사용하더라도 용량과 품질을 최적화할 수 있다.
VOD에서는 다음 기준이 중요하다.
- 최종 화질
- 파일 크기
- 저장 비용
- 품질 측정
- 자막/다국어 오디오 처리
- 재처리 가능성
Live
Live는 지금 들어오는 영상을 거의 실시간으로 처리해야 한다. 인코딩이 늦어지면 그대로 지연시간이 증가하고, 심하면 방송이 끊긴다.
Live에서는 다음 기준이 중요하다.
- 인코딩 속도
- 지연시간
- 안정성
- 장애 복구
- segment 생성 속도
- 플레이어 버퍼링 최소화
그래서 VOD에서는 CPU 기반 고품질 인코딩을 선택할 수 있지만, Live에서는 NVENC나 QSV 같은 하드웨어 인코딩이 더 현실적일 수 있다.
품질 측정도 필요하다
처음에는 눈으로 봐서 괜찮으면 충분하다고 생각할 수 있다. 하지만 여러 버전의 영상을 비교하거나, ladder를 자동화하려면 객관적인 지표가 필요하다.
대표적인 품질 지표는 다음과 같다.
| 지표 | 특징 |
|---|---|
| PSNR | 계산이 단순하지만 체감 품질과 항상 일치하지는 않음 |
| SSIM | 구조적 유사도를 측정 |
| VMAF | 체감 품질에 더 가깝게 평가하려는 지표 |
예를 들어 FFmpeg에서 VMAF를 측정하는 명령은 다음과 같은 형태로 사용할 수 있다.
ffmpeg -i encoded.mp4 -i source.mp4 \
-lavfi libvmaf \
-f null -
다만 품질 지표도 절대적인 답은 아니다. 실제 사용자 경험은 화질뿐 아니라 시작 시간, 버퍼링, 품질 전환 빈도, 디바이스 호환성, 네트워크 상태까지 함께 영향을 받는다.
내가 내린 결론
처음에는 트랜스코딩을 “영상 파일 변환” 정도로 이해했다. 하지만 정리해보니 트랜스코딩은 단순한 변환 작업이 아니라, 사용자 경험과 운영 비용 사이에서 균형을 잡는 설계 문제에 가깝다.
특히 스트리밍 서비스에서는 다음 네 가지를 동시에 고려해야 한다.
- 사용자의 네트워크 상황
- 디바이스와 브라우저 호환성
- 저장 및 전송 비용
- 인코딩 속도와 품질
ABR ladder는 다양한 네트워크 환경을 대응하기 위한 구조이고, FFmpeg는 이 구조를 실험하고 구현하기 위한 강력한 도구다. NVENC와 Quick Sync는 인코딩 속도와 처리량을 개선하는 선택지이고, CMAF는 HLS와 DASH를 더 효율적으로 운영하기 위한 패키징 관점의 기술로 이해할 수 있다.
결국 중요한 것은 특정 기술 이름을 외우는 것이 아니라, 프로젝트의 제약 조건을 보고 적절한 조합을 선택하는 것이다.
예를 들어 다음처럼 판단할 수 있다.
| 상황 | 우선 고려할 선택 |
|---|---|
| 빠르게 MVP를 만들고 싶다 | H.264 + AAC + HLS |
| VOD 품질과 용량을 최적화하고 싶다 | libx264/libx265 + CRF 실험 |
| 라이브 트랜스코딩이 필요하다 | NVENC 또는 Quick Sync 검토 |
| HLS와 DASH를 함께 제공하고 싶다 | CMAF 기반 fMP4 segment 검토 |
| 다양한 콘텐츠를 대규모로 처리한다 | per-title ladder, VMAF 측정 검토 |
마무리
이번 글을 통해 내가 이해한 핵심은 다음과 같다.
- 트랜스코딩은 단순한 파일 변환이 아니라 스트리밍 품질과 비용을 조절하는 핵심 과정이다.
- ABR ladder는 다양한 네트워크 환경에서 끊김을 줄이기 위해 여러 품질 단계를 준비하는 방식이다.
- FFmpeg는 트랜스코딩을 실험하고 구현하기 위한 강력한 도구이며,
ffprobe로 원본을 분석하는 습관이 중요하다. - NVENC와 Quick Sync는 빠른 처리에 유리하지만, 항상 최고 품질을 보장하는 것은 아니므로 프로젝트 조건에 따라 선택해야 한다.
- CMAF는 코덱이 아니라 HLS와 DASH가 공통 segment를 활용하기 쉽게 만드는 패키징 관점의 기술로 이해할 수 있다.
이 글을 한 문장으로 요약하면
트랜스코딩은 영상을 단순히 변환하는 작업이 아니라, 사용자 네트워크 환경, 디바이스 호환성, 화질, 비용, 지연시간 사이에서 최적의 균형을 설계하는 과정이다.
댓글 0
이름과 비밀번호를 입력하면 바로 댓글을 남길 수 있습니다.