WebRTC

primarchan·2024년 5월 25일

웹 관련 기술

목록 보기
1/2
post-thumbnail

안녕하세요, 오늘은 WebRTC에 대해 알아보겠습니다. WebRTC는 Web Real-Time Communication의 약자로, 웹 애플리케이션이나 사이트가 플러그인 없이도 브라우저 간에 실시간으로 오디오, 비디오 및 데이터를 주고받을 수 있도록 해주는 기술입니다. 요즘 같은 비대면 시대에 화상 회의, 라이브 스트리밍, 실시간 채팅 등 다양한 서비스에 활용되고 있습니다. 그럼 WebRTC가 무엇인지, 어떻게 동작하는지, 그리고 어떻게 사용되는지 함께 알아보겠습니다.

WebRTC의 주요 구성 요소

WebRTC는 주로 세 가지 요소로 구성됩니다.

  • RTCPeerConnection: 두 피어 간의 P2P 연결을 설정하고 제어합니다. 오디오, 비디오 스트림을 교환하는 역할을 합니다.
  • RTCDataChannel: 텍스트 또는 바이너리 데이터를 전송하는 데 사용됩니다.
  • getUserMedia(): 로컬 디바이스의 카메라나 마이크 같은 미디어 장치에 접근할 수 있게 해줍니다.

WebRTC의 동작 원리

WebRTC의 기본적인 동작 과정은 다음과 같습니다

  • 미디어 장치 접근: getUserMedia()를 통해 사용자의 카메라와 마이크에 접근합니다.
  • 피어 연결 생성: RTCPeerConnection 객체를 생성하여 피어 간의 연결을 설정합니다.
  • 신호 교환: ICE (Interactive Connectivity Establishment) 프로토콜을 사용해 신호 서버를 통해 후보(Candidate) 정보를 교환합니다.
  • 데이터 및 미디어 스트림 전송: 설정된 RTCPeerConnection을 통해 미디어 및 데이터 스트림을 전송합니다.

WebRTC 활용 예제

여기서는 Java를 이용한 WebRTC 예제를 소개하겠습니다. 이 예제에서는 Spring Boot를 사용해 신호 서버를 구현하고, 브라우저 간에 비디오 통신을 설정합니다.

  1. Maven 설정
    프로젝트의 pom.xml 파일에 다음 의존성을 추가합니다
<dependency>
    <groupId>org.java-websocket</groupId>
    <artifactId>Java-WebSocket</artifactId>
    <version>1.5.2</version>
</dependency>
  1. 서버 설정 (Spring Boot)
    Spring Boot 애플리케이션을 설정하여 WebSocket 서버를 만듭니다
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.*;
import org.java_websocket.server.WebSocketServer;
import org.java_websocket.handshake.ClientHandshake;
import org.java_websocket.WebSocket;

import java.net.InetSocketAddress;

@SpringBootApplication
public class WebrtcApplication {

    public static void main(String[] args) {
        SpringApplication.run(WebrtcApplication.class, args);
        WebSocketServer server = new WebSocketServer(new InetSocketAddress("localhost", 8080)) {
            @Override
            public void onOpen(WebSocket conn, ClientHandshake handshake) {
                System.out.println("New connection: " + conn.getRemoteSocketAddress());
            }

            @Override
            public void onClose(WebSocket conn, int code, String reason, boolean remote) {
                System.out.println("Closed connection: " + conn.getRemoteSocketAddress());
            }

            @Override
            public void onMessage(WebSocket conn, String message) {
                System.out.println("Message from client: " + message);
                for (WebSocket client : this.connections()) {
                    client.send(message);
                }
            }

            @Override
            public void onError(WebSocket conn, Exception ex) {
                ex.printStackTrace();
            }

            @Override
            public void onStart() {
                System.out.println("Server started successfully");
            }
        };
        server.start();
    }
}
  1. 클라이언트 설정
    HTML 파일에 다음과 같은 JavaScript 코드를 추가하여 클라이언트 측 WebRTC를 설정합니다:
<!DOCTYPE html>
<html>
<head>
    <title>WebRTC Example</title>
</head>
<body>
    <video id="localVideo" autoplay></video>
    <video id="remoteVideo" autoplay></video>
    <script>
        const localVideo = document.getElementById('localVideo');
        const remoteVideo = document.getElementById('remoteVideo');
        let localStream;
        let peerConnection;
        const config = {'iceServers': [{'urls': 'stun:stun.l.google.com:19302'}]};
        const socket = new WebSocket('ws://localhost:8080');

        async function start() {
            localStream = await navigator.mediaDevices.getUserMedia({video: true, audio: true});
            localVideo.srcObject = localStream;
            peerConnection = new RTCPeerConnection(config);
            peerConnection.addStream(localStream);

            peerConnection.onaddstream = (event) => {
                remoteVideo.srcObject = event.stream;
            };

            peerConnection.onicecandidate = (event) => {
                if (event.candidate) {
                    socket.send(JSON.stringify({'candidate': event.candidate}));
                }
            };

            socket.onmessage = async (message) => {
                const data = JSON.parse(message.data);
                if (data.candidate) {
                    await peerConnection.addIceCandidate(data.candidate);
                } else if (data.sdp) {
                    if (data.sdp.type === 'offer') {
                        await peerConnection.setRemoteDescription(new RTCSessionDescription(data.sdp));
                        const answer = await peerConnection.createAnswer();
                        await peerConnection.setLocalDescription(answer);
                        socket.send(JSON.stringify({'sdp': peerConnection.localDescription}));
                    } else if (data.sdp.type === 'answer') {
                        await peerConnection.setRemoteDescription(new RTCSessionDescription(data.sdp));
                    }
                }
            };

            const offer = await peerConnection.createOffer();
            await peerConnection.setLocalDescription(offer);
            socket.send(JSON.stringify({'sdp': peerConnection.localDescription}));
        }

        start();
    </script>
</body>
</html>

위 예제에서는 getUserMedia()를 사용해 로컬 미디어 장치에 접근하고, RTCPeerConnection을 통해 피어 간의 비디오 스트림을 교환합니다. 또한 WebSocket을 사용해 신호 교환을 처리합니다.

WebRTC는 실시간 통신 애플리케이션 개발을 혁신적으로 바꾸고 있습니다. 이를 통해 다양한 실시간 애플리케이션을 손쉽게 구현할 수 있으며, 앞으로도 많은 가능성을 열어줄 것으로 보입니다. 여러분도 WebRTC를 활용해 다양한 아이디어를 실현해보면 좋을 것 같습니다.

감사합니다.

레퍼런스

WebRTC 공식 문서
MDN Web Docs - WebRTC

profile
3년차 백엔드 개발자입니다.

0개의 댓글