본문 바로가기
Develop

FCM 알림 시스템 구현

by 너드나무 2022. 5. 9.
728x90

필요사항 정리

  1. 그룹 푸시 형태의 API 구성 (https://fcm.googleapis.com/fcm/notification 활용)
  2. FCM Token 테이블 구성
  3. FCM Token 생성 및 수정 (로그인 등) 시 POST /function/fcm 활용 Token 매칭 저장
  4. FCM Token 삭제 (로그아웃) 시 DELETE /function/fcm 활용 고객 식별 정보 매칭 삭제

FCM API 정리

# Push Group 생성
# 동일한 notification_key_name 생성 시 400 Error Return
# {"error":"notification_key already exists"}
notification_key = requests.post(
  "https://fcm.googleapis.com/fcm/notification",
  headers={
    "Authorization": f"key={FCM_KEY}",
    "Content-Type": "application/json",
    "project_id": FCM_PROJECT_ID
  },
  json={
    'operation': 'create',
    "notification_key_name":notification_key_name,  # 동일 name 생성 불가능
    "registration_ids":[  # 1,000개씩 관리 필요
      "FCM Token #1",
      "FCM Token #N"
    ]
  }
)

# Push Group 조회
notification_key = requests.get(
  "https://fcm.googleapis.com/fcm/notification",
  headers={
    "Authorization": f"key={FCM_KEY}",
    "Content-Type": "application/json",
    "project_id": FCM_PROJECT_ID
  },
  params={
    "notification_key_name":notification_key_name
  }
)

# Push Group Token 추가
notification_key = requests.post(
  "https://fcm.googleapis.com/fcm/notification",
  headers={
    "Authorization": f"key={FCM_KEY}",
    "Content-Type": "application/json",
    "project_id": FCM_PROJECT_ID
  },
  json={
    'operation': 'add',
    "notification_key_name":notification_key_name,  # 동일 name 생성 불가능
	  "notification_key": notification_key,
    "registration_ids":[  # 1,000개씩 관리 필요
      "FCM Token #1",
      "FCM Token #N"
    ]
  }
)

# Push Group Token 삭제
notification_key = requests.post(
  "https://fcm.googleapis.com/fcm/notification",
  headers={
    "Authorization": f"key={FCM_KEY}",
    "Content-Type": "application/json",
    "project_id": FCM_PROJECT_ID
  },
  json={
    'operation': 'remove',
    "notification_key_name":notification_key_name,  # 동일 name 생성 불가능
	  "notification_key": notification_key,
    "registration_ids":[  # 1,000개씩 관리 필요
      "FCM Token #1",
      "FCM Token #N"
    ]
  }
)

# 200 성공 시 notification_key Return
# {
#    "notification_key": "APA91bGHXQBB...9QgnYOEURwm0I3lmyqzk2TXQ"
# }
notification_key = json.loads(notification_key.text)['notification_key']

# Push 발송 (단일 발송과 동일)
fcm_request = requests.post(
  "https://fcm.googleapis.com/fcm/send",
  headers={
    "Authorization": f"key={FCM_KEY}",
    "Content-Type": "application/json"
  },
  json={
    'to': notification_key,
    "priority":"high",
    "notification":{
        "title":"그룹 푸시 테스트",
        "body":"푸시 테스트 내용입니당"
    }
  }
)
# 200 성공 시, 전체 성공 및 일부 실패
# {
#   "success": 2,
#   "failure": 0
# }
# {
#   "success":1,
#   "failure":2,  # 일부 실패 발생 시 Token Row 삭제 필요
#   "failed_registration_ids":[
#      "regId1",
#      "regId2"
#   ]
# }

 

구현 시나리오

  1. FCM Table 구성
    1. 대상 식별 정보
    2. FCM Token
    3. 마지막 저장시간
  2. 토큰 관리 체계
    1. 삭제된 토큰 제외처리 필요
    2. 만료된 토큰 제외처리 필요 (FCM Table 우선 Update 작업)
    3. 추가된 토큰 add 필요
  3. Mobile or Admin은 Backend 서버에 메시지 발송 요청을 보냄
  4. Backend 서버는 인가된 사용자 그룹인지 확인하고 message 구성
  5. Backend 서버 내부에서는 FCM에 해당 그룹에 속한 모든 기기에게 메세지 발송 요청
  6. FCM은 Messaging Group의 테이블로부터 Token 리스트 확인
  7. FCM은 해당 Mobile에 메세지 발송
  8. 그룹 푸시 이벤트 로직
    1. 이벤트 발생 API 발생 이후 푸시 이벤트 def notification 호출
      1. 인자값 : 그룹 id, 그룹 token List, notification Model
      2. if 그룹 token List > 1000: threading 적용
    2. notification key로 def send 호출
      1. error 발생 시 해당 fcm token 삭제 필요
  9. Token 삭제 로직
    1. 개별, 그룹 푸시 발송 시 faliure → token row delete
      1. 그룹 token 삭제 notification - remove (1)
      2. token table 삭제 (2)
    2. 오래된 토큰 기준 : 2달
  10. FCM Token DB 저장 시 유의사항
    1. 식별번호는 다른데 fcm token이 동일할 경우 (한 기기에서 다른 계정 접속 경우)
      1. 기존에 사용된 fcm token row는 삭제 → 식별번호 여러개 토큰 동일 방지
728x90
반응형