일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
- CS
- springboot
- findById
- DB replication
- 스케일아웃
- BFS
- 산업은행it
- 트리셋
- JPA
- 산업은행청년인턴
- 임베디드타입
- 컴퓨터구조
- 코테
- 그래프탐색
- CPU스케줄링
- 트리맵
- SpringBatch
- 해시
- Spring JPA
- 폰켓몬
- 백준
- flyway
- 2178
- 구현
- fatch
- 파이널프로젝트
- 운영체제
- 외래키제약조건위반
- 프로그래머스
- 프로젝트
- Today
- Total
나 JAVA 봐라
[Spring Boot] SSE로 알림 기능 구현하기 본문
크루장이 크루 신청을 승인 했을 때, 내가 쓴 게시글에 댓글이 달렸을 때,.. 등 사용자에게 알림이 가도록 하기 위해 알림 기능을 구현하려고 한다.
먼저 알림 기능을 위해 사용되는 방법 4가지를 간략하게 정리해보았다.
1. Polling
- 일정 주기로 서버 API 호출하는 방법
- 주기가 길다면? : 데이터의 실시간성을 보장할 수 없다.
- 주기가 짧다면? : 갱신된 내용 없어도 불필요한 요청이 자꾸 들어오기 때문에 불필요한 서버 부하가 발생한다.
2. Long Polling
- 업데이트 발생 시에만 응답을 보내는 방법. 서버에 요청 들어왔으면 일정 시간 대기하다가 업데이트 된 내용이 있을 경우 웹 브라우저에 응답을 보낸다.
- 불필요한 응답을 주는 경우를 줄일 수 있다. (장)
- 연결이 되어있는 경우 실시간으로 데이터가 올 수 있다. (장)
- 데이터 업데이트가 빈번할 경우, 연결을 위한 요청이 계속 발생하기에 서버 부하 발생한다. (단)
3. SSE (Server-sent Event)
- 웹브라우저에서 서버 쪽으로 특정 이벤트를 구독하면, 서버에서 해당 이벤트 발생 시에 웹 브라우저로 이벤트를 보내주는 방법
- 서버에서 웹 브라우저로만 데이터 전송 가능(단방향)
- 최대 동시 접속 횟수가 제한되어있다.
- 한번만 연결요청 보내면, 연결 종료 전까지는 재연결 없이 계속 데이터를 전송할 수 있다. (안끊김)
4. Web Socket
- 서버와 웹브라우저 사이 양방향 통신이 가능한 방법. 변경 사항에 빠르게 반응해야하는 채팅 등에 사용된다.
- 양방향 통신이 지속적으로 이루어진다.
- 연결을 유지하는 것 자체가 비용이 들기에, 트래픽 많으면 서버에 부담이 된다.
알림의 경우 전통적인 client-server 모델의 http 통신에서는 구현하기 어렵다. 해당 방식은 클라이언트의 요청이 있어야만 서버가 응답하는데, 알림은 ‘클라이언트의 요청이 없이’ 실시간으로 서버의 변경 사항이 웹 브라우저에 갱신 되어야하기 때문이다.
제시된 4가지 방법 중 http 연결에 대한 부담이 적은 방식은 SSE, Web socket 이며 실시간성도 보장이 된다. 이 중 알림은 단방향 통신만 해도 된다. (서버 → 클라이언트) 그래서 보통 알림은 SSE 방식을 많이 채택한다.
알아보니 Spring에서 제공하는 SSE 프레임워크 사용하면 알람 기능이 쉽게 구현될 것 같아 SSE 방식의 알림 기능을 구현하기로 정했다.
크게 보면 작업은 아래와 같이 진행될 것이라 예상된다.
- 웹 브라우저와 서버 연결하기 (한번 연결하면 재연결 자주 안해도 된다.)
- 연결 관련해서 설정해주기 (연결 , 알림 전송 메소드 생성 포함)
- 생성해둔 알림 전송 메소드를 각 이벤트가 발생하는 서비스 메소드 내에 추가한다.
- 크루장 승인의 경우, 승인 메소드 내에 알림 전송 메소드 포함하여 알림 전송될 수 있도록 한다.
이 때, 팀에서 고민했던 내용들이 있다.
Q. SSE는 실시간 접속 중일 때만 알림을 보낼 수 있다. 사용자가 오프라인일 때는 어떻게 할지?
위의 질문에 대해 3가지 해결 방법을 생각해보았다.
A.
- 서버가 사용자의 접속여부를 파악하여서 따로 처리한다. 이 때, 지금 프로젝트는 토큰 방식으로 인증을 하기에, 서버에서 사용자의 접속 여부 알 수 없다. 따라서 접속여부 파악하는 방법?
- 접속여부 DB 생성하고, 클라이언트에서 heartbeat 5초에 한번씩 서버로 보내서 접속 여부 파악 → 주로 프론트 개발자가 해야할 일들이라서 패스
- 푸시 알람 전송하기. SSE의 경우 오프라인일 경우 실시간 전송이 안됨. 물론 푸시 알림으로 처리할 수 있지만 이 부분은 프론트 개발자가 처리해야해서 일단 패스
- 알림함 만들기. 특정 이벤트가 발생했을 때, 아래의 a,b 두 가지를 모두 실행한다.
- SSE로 실시간 알림을 전송한다 →
- 만약 오프일 경우, 그냥 알림 못받는 것으로 처리
- 온라인일 경우, 알림함 빨간 표시 + 팝업창 띄우기 정도
- 알림함 DB에 알림 내용을 저장한다. → 온, 오프 상관 없이 모두 DB에 저장하고, t/f로 읽음 여부 판단하기
- 알림함은 최초 접속 1회일 때만 조회해서 안읽은 알람 여부 판단하고, 이 후 실시간 알람 왔을 때에만 알림함 한번씩 조회하기. (실시간 알림 안왔으면 알림 조회할 이유 없으니까)
- SSE로 실시간 알림을 전송한다 →
⇒ 결론으로는 3번째 방법으로 진행하기로 했다.
참고
https://taemham.github.io/posts/Implementing_Notification/
[백엔드 스프링부트] 알림 기능은 어떻게 구현하는게 좋을까?
This is a wannabe backend developer’s dev blog.
taemham.github.io
'프로젝트' 카테고리의 다른 글
[학부 연구] 자기지도학습을 통한 신장분할 (0) | 2024.04.14 |
---|---|
Boot-Up : 개발 전 시동 걸기 (1) | 2023.12.20 |