Notice
Recent Posts
Recent Comments
Link
반응형
«   2026/01   »
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
Archives
Today
Total
관리 메뉴

coding etude

[Flutter] Socket_io_client 채팅기능을 만들어보자(1) 본문

Flutter(Dart)

[Flutter] Socket_io_client 채팅기능을 만들어보자(1)

코코리니 2026. 1. 28. 01:23
반응형

webSocket 과 socket.io 중 왜 socket.io를 선택 했을까?

기능과 편의성을 위해서 선택했다.

그럼, 이 둘의 차이점을 알아야 상황별로 어떤 것을 사용 하느냐를 정할 수있겟지.

검색하면 다 나오는 내용이니 간략하게 만 정리하자면.

webSocket은 프로토콜, socket.io는 라이브러리 이다.

프로토콜은 다들 알겠지만, 우리 이렇게 합시다~ 라고 명시된 규약이다.

말 그대로 양방향  실시간 소통을 위한 규약 이라고 생각하면 된다.

빠르고, 적은용량을 주고 받으며, 단순 주고 받는것만 가능하다.

반면, socket.io는 ws(webSocket)를 활용해서 만들어진 라이브라리.

단순 주고 받는 기능을 포함하여, room 과 broadcast 기능을 이용하여 하나의 채팅방에 소속된 사용자들을 

세밀하게 관리가 가능하게 해준다.

참고로 서버에서 socket.io를 사용 한다면, Flutter에서는 Socket_io_client를 사용해야한다.

web 전용 socket.io를 flutter에서 사용 할 수 있게 dart언어로 변환한 package 이다.

 

socket (socket_io_client) 의 속성과 기능

socket에 속한 주요 기능은 다음과 같다.

io(): 초기 서버의 도메인을 등록하고 socket을 생성.

connect(): 초기화 된 socket을 서버의 socket과 연결.

onConnect(): connect() 이후 연결이 완료된 후 실행.

connected : 서버와 연결이 되어 있는지 bool 값을 return.

leave(): 서버에 join된 채팅방에서 연결 해제.

emit(): 서버로 이벤트 명(name)과 데이터를 전송

dispose(): socket 종료.

disconnect(): 서버와 연결 해제.

 

socket의 핵심 구동 원리

1. Stream 

socket을 사용하는 이유는 서버로 보낸 내용을 실시간으로 상대방에게 전송해주고, 상대방이 전송한 내용을 사용자가 실시간으로 확인하는 기능을 사용하기 위해서이다. 이 실시간 소통을 유지하려면 Flutter에서는 stream 기능을 사용해야한다.

다 알고 있겠지만, Flutter의 stream기능은 데이터를 지속적으로 받는 기능이고 원하는 데이터를 받을 시 해당 데이터만 return 할 수 있는 기는이다. 1회성인 Future(async/await)와의 차이점이다.

( 그래서 스트리밍 중이라는 말은 데이터를 실시간으로 유지하고 있다는 뜻!! 깨알 상식😉 )

이 stream은 앱 실행 시 초기에 한번만 listener를 등록해 놓으면 stream을 수동으로 cancel 하거나 앱 종료(dispose) 하지 않는 이상 계속 유지가 된다.

 

2. room & broadcast

socket은 각각의 채팅방을 따로 controller 할 수 있다. 각 방을 room 이라고 하고, room에 속한 모든 사용자에게 내용을 전달 하는것을 broadcast라고 한다.

예를 들어 5명이 있는 채팅에서 사용자가 메시지를 전송하면, 서버에서 비지니스 로직을 거친후 생성된 message를 roomId를 통해서 room에 속한 5명에게 동시에 전달해주는 시스템이다. 그래서 flutter에서도 동일하게 roomEntity, roomMemberEntity, messageEntity가 필요하다. 

socket의 실행 순서

App 실행 |
               |- initialize() + stream listener 등록
               |- 채팅방 입장 -> connect() + onConnect() -> joinRoom()
               |- sendMessage() 
               |- 채팅방 퇴장 -> leave()
               |- logout -> disconnect()

 

코드 예시 

Socket.io? _socket;
// stream controller
final StreamController<Map<String, dynamic>> _controller =
  StreamController<Map<String, dynamic>>.broadcast();
  
// initalize
void init(Sting token, String host){
  _socket = IO.io(host, IO.OptionBuilder()
    .setTransports(['websocket']) // websocket 전용
    .setAuth({'token': token})
    .disableAutoConnect() // connect() 수동 제어
    .build()
  );
  
  // stream controller 이벤트 등록
  // onAny(): 서버에서 전송된 모든 이벤트 받음.
  // on(event, data): 서버에서 전송된 특정 이벤트만 받음.
  // 모든 이벤트를 stream controller에 추가.
  _socket.onAny((event, data) {
    _controller.add({
      'event' : event,
      'data' : data
    });
  });
}

// connect
void connect() {
  _socket.connect()
}
void join (int roomId) {
  // 서버의 이벤트 네임과 동일해야함.
  _socket.emit('join_room', roomId);
}
void sendMessage(MessageEntity message){
  _socket.emit('chat_message', message);
}
void leaveRoom(int roomId){
  _socket.emit('leave room', roomId);
}
void disconnect(){
  _socket.disconnect();
}

//!! 중요 Stream 설정
// onAny()에서 이벤트 전송 받으면 _controller로 전송
// _controller 에서 eventName과 같은 이벤트라면(where) data를 return 해준다.
Stream<T> subscribeEvent<T> (String eventName, T Function(dynamic data) mapping) {
  return _controller.stream
    .where((event) {
      return event['event'] == eventName;
    }).map((event){
      return mapping(event['data]);
    })
}

 

오늘은 socket에 대한 이론적인 부분과 설정 예시코드를 정리 했다.

다음 포스팅에서는 실제 flutter code에서 언제 어디서 어떤 방식으로 사용 되는지 알아보자!

 

끝.

반응형