React Native) push notification on/off 기능 추가하기

2ast·2023년 1월 24일
0
post-custom-banner

만약 스토어에 notification 기능을 제공하는 앱을 업로드하려고 한다면, 반드시 notification on/off 기능을 추가해야한다. 그렇지 않으면 스토어 정책에 의해 앱 업로드가 거부될 수 있기 때문이다.

notification on/off를 수행하는 방법에는 여러가지가 있을 수 있다.

  1. on/off 여부를 서버로 보내 서버에서 이를 판단한 뒤 아예 푸시를 발송하지 않는 방법
  2. on/off 여부를 클라이언트에서 갖고 있고, push가 오더라도 이를 판단해 노출하지 않는 방법
  3. off 버튼을 누르면 해당 앱 알림 설정으로 리다이렉트 시켜, 스마트폰 단에서 알림을 거부하도록 하는 방법
  4. off 버튼을 누르면 이전에 발급했던 fcm token을 무효화시켜 푸시 발송을 막는 방법

이 밖에도 여러가지 방법이 있을 수 있다. off했을 경우 사용자에게 notification을 노출하지 않기만 하면 되기 때문이다. 이번에는 이중에서 이전 fcm token을 무효화하는 방법을 구현해보려고 한다.

사전 준비

먼저 이 방법을 위해서는 local storage가 필요하다. RN local storage 라이브러리 중에서 가장 대중적인 라이브러리를 설치해서 진행할 예정이다.

yarn add @react-native-async-storage/async-storage
cd ios && pod install && cd ..

on/off 버튼 만들기

뷰보다는 기능 구현이 우선이기에 설정 페이지에 RN의 Switch를 이용해 기본적인 스위치를 하나 만들어보겠다.

import React, {useState} from 'react';
import {Switch, Text, View} from 'react-native';

const Settings = () => {
  const [isEnabled, setIsEnabled] = useState(true);
  const toggleSwitch = (value: boolean) => setIsEnabled(value);
  return (
    <View
      style={{
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        backgroundColor: 'white',
      }}>
      <Text>알림 {isEnabled ? '끄기' : '켜기'}</Text>
      <Switch
        trackColor={{false: '#767577', true: '#81b0ff'}}
        thumbColor={isEnabled ? '#f5dd4b' : '#f4f3f4'}
        ios_backgroundColor="#3e3e3e"
        onValueChange={toggleSwitch}
        value={isEnabled}
      />
    </View>
  );
};
export default Settings;

toggleSwitch에 AsyncStorage 연동하기

const toggleSwitch = (value: boolean) => {
    if (value) {
      AsyncStorage.setItem('notificationEnabled', 'true');
    } else {
      AsyncStorage.setItem('notificationEnabled', 'false');
    }

requestPermission에 AsyncStorage 연동하기

export async function requestUserPermission() {
  const authStatus = await messaging().requestPermission();
  const enabled =
    authStatus === messaging.AuthorizationStatus.AUTHORIZED ||
    authStatus === messaging.AuthorizationStatus.PROVISIONAL;

  const notificationEnabled = await AsyncStorage.getItem('notificationEnabled');
  
  if (enabled && JSON.parse(notificationEnabled ?? 'true')) {
    await messaging()
      .getToken()
      .then(fcmToken => {
        console.log('fcmToken:', fcmToken);
      })
      .catch(e => console.log('error: ', e));
  }
}

getToken을 하기에 앞서 현재 push notification을 수신허용상태인지 확인하고, true일 때만 다음 단계로 진행하도록 해주었다.

toggleSwitch에 getToken, deleteToken 연동

const toggleSwitch = (value: boolean) => {
    if (value) {
      AsyncStorage.setItem('notificationEnabled', 'true').then(() =>
        requestUserPermission(),
      );
    } else {
      AsyncStorage.setItem('notificationEnabled', 'false').then(() =>
        messaging().deleteToken(),
      );
    }
    setIsEnabled(value);
  };

switch initail state 설정

설정 페이지로 이동했을 때 AsyncStorage를 참조해서 switch의 초기상태를 설정해주는 과정도 추가하면 좋다.

const Settings = () =>{
  ...
   useLayoutEffect(() => {
    AsyncStorage.getItem('notificationEnabled').then(enabled => {
      if (!JSON.parse(enabled ?? 'true')) {
        setIsEnabled(false);
      }
    });
  }, []);
  ...
}
export default Settings

예시케이스가 간단하기 때문에 이정도로 충분하지만, 만약 fcm token을 서버에도 저장중이라면 toggleSwitch에 mutation까지 함께 적용해주면 된다.

profile
React-Native 개발블로그
post-custom-banner

0개의 댓글