웹소켓 재접속 예제 - 서버, 클라이언트

햄스터아저씨·2023년 2월 17일
0

클라이언트에서 웹소켓 연결이 끊긴 경우,
서버와 연결이 될 때까지 무한히 재시도하는 코드

서버코드(파이썬)

설명

  • 연결된 유저에게 랜덤한 숫자를 json 으로 1초마다 송신한다
import asyncio
import websockets
import random
import json

async def handler(websocket, path):
    while True:
        # 100 ~ 2000 사이의 랜덤한 숫자를 연결된 유저에게 전송합니다.
        number = random.randint(100, 2000)
        print(number)
        res = {
            "number": number
        }
        await websocket.send(json.dumps(res))
        await asyncio.sleep(1)

async def main():
    async with websockets.serve(handler, "localhost", 8080):
        await asyncio.Future()

asyncio.run(main())

클라이언트 코드(리엑트)

설명

  • 서버로부터 웹소켓을 통해 받은 json 내용을 출력한다
  • 서버의 연결이 끊긴 경우, 다시 연결에 성공할 때까지 연결을 재시도한다
  • 서버의 연결상태를 출력한다.
import { useEffect, useState } from "react";

function MyComponent() {
  const [socket, setSocket] = useState(null);
  const [socketState, setSocketState] = useState("Closed");
  const [data, setData] = useState(-1);

  const connect = (prevState) => {
    /* 
      이 함수는 웹소켓 연결을 생성하고, 웹소켓을 통해 들어온 데이터를 처리합니다.

      * 이 함수는 단 1개의 연결만 생성하는 것을 보장합니다.
      * 다만 에러로 인한 페이지갱신이 발생할 경우, 연결을 시도하는 웹소켓 갯수가 늘어날 위험은 있습니다.
      * 연결이 끊긴 경우, 스스로 재연결을 시도합니다.
      * 이 함수는 동작을 위해 prevState와 socketState 상태를 필요로 합니다.
    */

    if (prevState === "Closed" && socketState === "Closed") {
      console.log("Connecting...");
      const newSocket = new WebSocket("ws://localhost:8080");
      setSocket(newSocket);

      newSocket.onmessage = (event) => {
        const res = JSON.parse(event.data);
        setData(res.number);
        console.log(event);
      };

      newSocket.onopen = (event) => {
        setSocketState("Open");
      };

      newSocket.onclose = (event) => {
        setSocketState("Closed");
        connect(socketState);
      };
    }
  };

  useEffect(() => {
    connect("Closed");
    return () => {
      // socket.close(); // Cannot read properties of null (reading 'close')
    };
  }, []);

  return (
    <div>
      <p>서버 연결 상태: {socketState}</p>
      <p>{data}</p>
    </div>
  );
}

export { MyComponent };

예시 결과

연결되지 않은 경우

연결된 경우

연결이 끊긴 경우

  • 출력
    마지막 값이 유지된 상태로, 연결 상태값만 변경된다

  • 로그
    지속적으로 재시도함을 알 수 있다.
profile
서버도 하고 웹도 하고 시스템이나 인프라나 네트워크나 그냥 다 함.

0개의 댓글