포스트

ws로 웹소켓 사용하기

안녕하세요 🐸

웹소켓을 사용하는 방법 중 ws 를 사용하는 방법에 대해 정리해보겠습니다.

설치

1
npm i ws

웹소켓 파일 작성

서버가 ws 프로토콜에 응답할 수 있도록 하는 코드입니다.
그리고 서버가 클라이언트로 메세지를 보내는 내용이 포함되어 있습니다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
const WebSoket = require('ws');

module.exports = (server)=>{
    const was = new WebSoket.Server({server});

    was.on('connection',(ws,req)=>{
        const ip = req.headers['x-forwarded-for'] || req.socket.remoteAddress; // 클라이언트의 IP
        console.log('새로운 클라이언트 접속',ip);
        ws.on('message',(message)=>{ // 클라이언트가 보내는 매세지에 응답
            console.log(message.toString());
        })

        ws.on('error',console.error); // 에러 발생 시

        ws.on('close',()=>{
            console.log('클라이언트 접속 해제',ip);
            clearInterval(ws.interval);
        });

        ws.interval = setInterval(()=>{
            if(ws.readyState === ws.OPEN){
                ws.send('서버에서 클라이언트로 메시지를 보냅니다.');
            }
        },3000)
    })
}

코드 분석

1
const was = new WebSoket.Server({server});

서버가 ws 프로토콜에 응답할 수 있도록 붙여주고 결과를 변수로 저장합니다.
여기서 변수에 저장하는 이유는 현재 상태로는 ws 프로토콜에 응답할 수 있는 상태가 되었을 뿐, 실제로 연결 후의 이벤트는 없기 때문입니다.

1
was.on('connection',(ws,req)=>{})

웹소켓 서버가 클라이언트와 연결합니다.
여기서 첫 번째 파라미터는 클라이언트와 연결된 웹소켓 인스턴스 입니다.


브라우저에서 웹소켓으로 연결하기

아래는 브라우저의 WebSoket 라이브러리를 사용한 코드로, 앞서 서버에서 사용한 ws 라이브러리와는 다릅니다.
그렇기 때문에 이벤트 감지도 서버와는 다르게 onopen() , onmessage() 등을 사용하고 있습니다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
<script>
	const webSoket = new WebSocket('ws://localhost:8005');

	webSoket.onopen = function(event) {
		console.log('WebSocket 연결 성공!');
		webSoket.send('안녕하세요!');
	};

	webSoket.onmessage = function(event) {
		console.log('서버로부터 받은 메시지:', event.data);
	};

	webSoket.onclose = function(event) {
		console.log('WebSocket 연결 종료됨!');
	};

	webSoket.onerror = function(event) {
		console.error('WebSocket 오류 발생:', event);
	};

	webSoket.onclose = function(event) {
		console.log('WebSocket 연결 종료됨!');
	};

	// 메시지 전송 예시
	function sendMessage(message) {
		if (webSoket.readyState === WebSocket.OPEN) {
			webSoket.send(message);
		} else {
			console.error('WebSocket이 열려 있지 않습니다. 메시지를 전송할 수 없습니다.');
		}
	}
	// 예시로 3초마다 메시지 전송
	setInterval(() => {
		sendMessage('3초마다 전송되는 메시지');
	}, 3000);
</script>

웹소켓 연결 상태

상태설명
CONNECTING연결 중
OPEN연결됨
CLOSING연결 종료 중
CLOSE연결 종료됨

웹소켓 서버 이벤트 & 웹소켓 인스턴스 이벤트

웹소켓 서버 이벤트

이벤트 이름설명
connection클라이언트가 연결될 때 발생. 가장 많이 씀.
error서버에서 에러 발생 시.
headers클라이언트의 핸드셰이크 요청 헤더가 들어올 때. 헤더를 조작할 수도 있음.
close서버가 종료될 때 발생.
wsClientError클라이언트 측의 WebSocket 핸드셰이크 중 오류가 생겼을 때 (v8 이후 비공식).

여기서 저는 connection 외에는 사용해보지 못했습니다.

웹소켓 인스턴스 이벤트

이벤트 이름설명
message클라이언트로부터 메시지를 받았을 때
error소켓에 오류가 발생했을 때
close연결이 종료됐을 때
ping / pong핑/퐁 신호 수신 시 (연결 상태 확인용)
unexpected-response핸드셰이크 중 HTTP 응답이 예상과 다를 때 (클라이언트에서 유용)
open클라이언트에서 연결이 열린 후 (보통 브라우저 측 WebSocket에 해당)
upgrade서버에서 HTTP → WebSocket 업그레이드 시 (거의 사용 X)
redirect일부 클라이언트 환경에서 지원 (브라우저 위주)

일반적으로 message, error, close 는 주로 쓰입니다.
unexpected-response 이 이벤트는 클라이언트 측에서 웹소켓 연결 요청을 시도했으나 서버에서 모종의 이유로 연결을 거부할 때 정확한 이유를 분석할 때 유용합니다.
하지만 브라우저의 웹소켓 라이브러리에서는 unexpected-response 을 따로 이벤트로써 감지하지 않습니다.


참고 https://masteringjs.io/tutorials/node/websocket-server
https://www.npmjs.com/package/ws#simple-server

이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.