본문으로 건너뛰기

Stimulus와 MediaRecorder API를 활용한 Rails 앱 내 비디오 녹화 기능 구현 가이드

Record video in Rails with Stimulus | Rails Designer

작성자
발행일
2026년 02월 19일
https://railsdesigner.com/recording-video-stimulus/

핵심 요약

  • 1 브라우저의 MediaRecorder API와 Stimulus를 결합하여 외부 라이브러리 없이 웹캠 및 화면 녹화 기능을 Rails 애플리케이션에 직접 구현할 수 있습니다.
  • 2 웹캠과 화면 공유 스트림을 HTML5 Canvas로 결합하여 구현하는 Picture-in-Picture(PiP) 모드는 사용자에게 보다 전문적인 녹화 경험을 제공하는 핵심 기술입니다.
  • 3 녹화된 데이터를 Blob 형태에서 File 객체로 변환하고 DataTransfer API를 활용해 Active Storage에 저장함으로써 Rails의 표준 파일 처리 워크플로우를 유지할 수 있습니다.

도입

본 가이드는 과거 jQuery 플러그인에 의존하던 비디오 녹화 기능을 최신 Hotwire와 Stimulus 환경으로 전환하는 구체적인 방법을 제시합니다. 외부 라이브러리나 복잡한 설정 없이 브라우저 표준 API인 MediaRecorder를 활용하여 웹캠 녹화, 화면 공유, 그리고 두 가지를 동시에 사용하는 Picture-in-Picture(PiP) 기능을 구현하는 과정을 다룹니다. 특히 Rails의 Active Storage와 연동하여 녹화된 영상을 서버에 저장하는 전체 워크플로우를 설명함으로써 현대적인 웹 개발 방식에 부합하는 솔루션을 제공하고자 합니다.

1. 개요 및 시스템 구조

이 구현의 핵심은 브라우저 내장 API인 MediaRecorder를 Stimulus 컨트롤러 내에서 체계적으로 관리하는 것입니다. 외부 서비스에 의존하지 않고 브라우저의 역량만으로 웹캠, 화면 공유, 그리고 이 둘을 결합한 혼합 모드를 지원합니다. Rails 백엔드와는 Active Storage를 통해 연결되며, 녹화가 완료된 영상은 즉시 서버로 전송되어 저장될 수 있는 구조를 가집니다.

2. Stimulus 컨트롤러 설계 및 상태 관리

recorder_controller.js는 녹화의 전 과정을 제어합니다. 주요 특징은 다음과 같습니다.

  • Targets & Values: preview(실시간 화면), video(녹화 후 재생), videoInput(파일 업로드용 input) 등을 타겟으로 지정하고, mode 값을 통해 현재 녹화 상태(webcam, screen, pip)를 추적합니다.
  • 연결 및 해제: connect()에서 초기 상태를 설정하고, disconnect()에서 활성화된 모든 미디어 트랙을 정지시켜 리소스 누수를 방지합니다.
  • 메서드 조직화: 인터페이스 역할을 하는 공개 메서드를 상단에 배치하고, 내부 로직을 담당하는 비공개 메서드(prefix #)를 하단에 배치하여 코드의 가독성과 전문성을 높입니다.

3. 미디어 스트림 획득 및 녹화 로직

사용자가 선택한 모드에 따라 적절한 API를 호출합니다.

  • Webcam: navigator.mediaDevices.getUserMedia를 사용하여 비디오와 오디오 권한을 획득합니다.
  • Screen: navigator.mediaDevices.getDisplayMedia를 통해 화면 공유 스트림을 가져옵니다.
  • MediaRecorder: 획득한 스트림을 MediaRecorder 객체에 전달합니다. ondataavailable 이벤트를 통해 전송되는 데이터 청크(chunks)를 배열에 수집하고, 녹화 중단 시 이를 하나의 Blob으로 결합합니다.

4. Canvas를 활용한 Picture-in-Picture(PiP) 구현

가장 기술적으로 흥미로운 부분은 화면 공유와 웹캠을 동시에 녹화하는 PiP 모드입니다.

  1. 스트림 합성: 화면 공유 스트림과 웹캠 스트림을 각각 생성합니다.
  2. Canvas 드로잉: 숨겨진 canvas 요소를 생성하고, requestAnimationFrame 루프 내에서 화면 스트림을 배경으로, 웹캠 스트림을 우측 하단에 오버레이로 그립니다.
  3. 스트림 추출: canvas.captureStream(30)을 호출하여 초당 30프레임의 새로운 합성 스트림을 생성하고, 이를 MediaRecorder에 전달하여 녹화합니다.

5. Active Storage와의 연동 및 저장

녹화가 완료된 후 서버에 저장하는 과정은 다음과 같은 단계를 거칩니다.

  • Blob to File: 수집된 데이터를 video/webm 타입의 Blob으로 만들고, 이를 다시 File 객체로 변환합니다.
  • DataTransfer 활용: 보안상의 이유로 파일 input의 값을 직접 수정할 수 없으므로, DataTransfer API를 사용하여 생성된 파일을 input에 주입합니다.
  • Form 제출: form.requestSubmit()을 호출하여 Rails 서버로 영상을 전송합니다. Rails의 Active Storage는 이를 일반적인 파일 업로드와 동일하게 처리합니다.

결론

Stimulus와 MediaRecorder API를 활용한 이 방식은 외부 의존성을 최소화하면서도 강력한 기능을 제공하는 현대적인 Rails 개발의 전형을 보여줍니다. 특히 Canvas를 이용한 스트림 합성이나 DataTransfer를 통한 파일 업로드 기법은 복잡한 프런트엔드 요구사항을 깔끔하게 해결하는 좋은 사례입니다. 코드 가독성을 위해 공개 메서드와 비공개 메서드를 분리하여 구성하는 Stimulus 컨트롤러 설계 원칙을 준수함으로써, 유지보수가 용이하고 전문적인 결과물을 얻을 수 있습니다.

댓글0

댓글 작성

댓글 삭제 시 비밀번호가 필요합니다.

이미 계정이 있으신가요? 로그인 후 댓글을 작성하세요.

0/1000
정중하고 건설적인 댓글을 작성해 주세요.