fix(backend): 붙잡은 직후 들어온 메일 하나에 알림이 두 번 가지 않게 한다

엔진 연결을 붙잡자마자 메일이 오면 따라잡기와 그 메일의 새 메일 신호가 함께 보내 알림이 두 번 갔다(커밋 전 다시 리뷰 N1).
붙잡은 뒤 신호를 이미 받았으면 따라잡기를 건너뛰고, 따라잡기 뒤 간격 끝의 보내기는 따라잡기가 센 뒤에 받은 메일이 있을 때만 보낸다
(기록 저장이 실패해도 겹치지 않게 메모리로 본다). 옛 주석의 "로그인이 저절로 끝남"을 끝난 까닭 표로 고치고 계약 · 스킬의 문장도 맞췄다.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-11-08 01:22:58 +09:00
parent b77f95fdff
commit 3f66f39f9d
8 changed files with 202 additions and 47 deletions
+3
View File
@@ -196,6 +196,9 @@
- **따라잡기**: 붙잡을 때마다(서버를 다시 띄움 · 다시 붙잡음) 그 전 10분 안 · 마지막으로 보낸 뒤 · 본 뒤에 온 안 읽은 메일이 있으면 그 기기에 그때의 N 으로 한 번 — 이미 알린 · 이미 본 메일로는 다시 울리지 않는다.
"보낸 뒤 · 본 뒤"는 `last_pushed_at`(그 알림의 N 을 센 때) · `seen_at` 의 **다음 초부터**다 — 받은 시각은 초라 그 초에 받은 메일은 그 알림에 이미 들었거나 이미 보았다고 본다(2026-11-07 리뷰). N 은 위처럼 `seen_at` 의 초부터 센다.
그 초에 센 · 본 뒤 들어온 메일은 따로 새 메일 신호를 낸다 — 그 알림이 나가기 전(그 1초 안 · 30초 간격의 끝을 기다리는 사이)에 서버가 멈추면 놓친다. 따라잡기로 보내도 30초 간격에 든다.
**붙잡은 직후의 메일 하나에는 한 번만 울린다**(2026-11-08 리뷰): 붙잡은 뒤 새 메일 신호가 먼저 왔으면 따라잡기는 건너뛴다(신호 쪽이 그때의 N 으로 보낸다).
따라잡기로 보낸 뒤 첫 신호 보내기는 따라잡기와 같은 규칙(`seen_at` · `last_pushed_at` 의 다음 초부터)으로 새로 받은 메일이 있는 기기에만 — 따라잡기가 센 메일의 신호가 뒤늦게 와도 간격 끝에 다시 울리지 않는다.
그래서 따라잡기가 센 그 초에 센 뒤 들어온 메일은 그 보내기에서 빠진다(다음 알림의 N 에는 든다).
**엔진의 `after` 는 그 초를 넣지 않는다**("그 초보다 뒤" — RFC 8621 은 "같거나 뒤"라 적는다, 2026-11-08 개발 엔진 0.16.27 에서 확인) — 서버는 한 초 앞을 넘겨 같은 초를 센다(`jmap-mail.provider.ts`). 엔진 판을 올리면 다시 본다(같은 초를 넣게 바뀌면 따라잡기가 이미 알린 메일로 한 번 더 울린다).
- **보내는 메시지** (FCM v1 `messages:send` 의 `message` — 서버 `modules/push/fcm/fcm-message.ts` 한 곳, 받는 것은 FID 와 개수뿐):
```json