@react-native-firebase/app package installed & setup.@react-native-firebase/messaging package installed & setup.Foreground - onMessage
Background, Quit - setBackgroundMessageHandler
android와 ios에서 background나 quit상태일때 data만 보내질경우 메세지를 무시해버린다.
onMessage : 앱이 실행되는 중이거나 백그라운드에 있을경우setBackgroundMessageHandler : 앱이 실행되어 있지 않은경우import messaging from '@react-native-firebase/messaging';
// Note that an async function or a function that returns a Promise
// is required for both subscribers.
async function onMessageReceived(message) {
// Do something
}
messaging().onMessage(onMessageReceived);
messaging().setBackgroundMessageHandler(onMessageReceived);
메세지를 보내기 위해서 메세지 토큰 이 필요하다. 이 토큰은 각 디바이스의 고유한 토큰으로 데이터베이스에 저장하고 FCM에 메세지가 보내질때 디바이스를 특정할 수 있음.
It is recommended you fetch and update the token each time the application boots in-case it has changed.
import messaging from '@react-native-firebase/messaging';
async function onAppBootstrap() {
// Register the device with FCM
await messaging().registerDeviceForRemoteMessages();
// Get the token
const token = await messaging().getToken();
// Save the token
await postToApi('/users/1234/tokens', { token });
}
IOS
IOS는 유저에게 허가를 받지 않으면 notification을 포함한 payload를 막기때문에 requestPermission로 유저의 허가를 요청하는 native permission dialog로 허가를 받는다.
IOS Permissions
import messaging from '@react-native-firebase/messaging';
async function requestUserPermission() {
const authStatus = await messaging().requestPermission();
const enabled =
authStatus === messaging.AuthorizationStatus.AUTHORIZED ||
authStatus === messaging.AuthorizationStatus.PROVISIONAL;
if (enabled) {
console.log('Authorization status:', authStatus);
}
}
norifiee를 이용할 경우
import notifee, { AuthorizationStatus } from '@notifee/react-native';
async function requestUserPermission() {
const settings = await notifee.requestPermission();
if (settings.authorizationStatus >= AuthorizationStatus.AUTHORIZED) {
console.log('Permission settings:', settings);
} else {
console.log('User declined permissions');
}
}
setting을 확안하고 싶다면
const settings = await notifee.requestPermission();
ios의 경우 Category를 android는 Group을 만들 수 있다
ios
action이란 알림창에서 바로 취할수 있는 버튼을 만들어주는데 버튼을 눌렀을경우 onBackgroundEvent에서 pressAction에 action의 id 값이 들어간다.
async function setCategories() {
await notifee.setNotificationCategories([
{
id: 'message',
actions: [
{
id: 'mark-as-read',
title: 'Mark as read',
},
],
},
]);
}
notifee.displayNotification({
title: 'New post from John',
body: 'Hey everyone! Check out my new blog post on my website.',
ios: {
categoryId: 'message',
},
});
import notifee, { EventType } from '@notifee/react-native';
notifee.onBackgroundEvent(async ({ type, detail }) => {
if (type === EventType.ACTION_PRESS && detail.pressAction.id === 'mark-as-read') {
console.log('User pressed the "Mark as read" action.');
}
});
notifee의 backgroundHandler가 동작 안되서 대체
getInitialNotification: When the application is opened from a quit state.onNotificationOpenedApp: When the application is running, but in the background.useEffect(() => {
// Assume a message-notification contains a "type" property in the data payload of the screen to open
messaging().onNotificationOpenedApp(remoteMessage => {
console.log(
'Notification caused app to open from background state:',
remoteMessage.notification,
);
navigation.navigate(remoteMessage.data.type);
});
// Check whether an initial notification is available
messaging()
.getInitialNotification()
.then(remoteMessage => {
if (remoteMessage) {
console.log(
'Notification caused app to open from quit state:',
remoteMessage.notification,
);
setInitialRoute(remoteMessage.data.type); // e.g. "Settings"
}
setLoading(false);
});
}, []);
ios에서 setBackgroundMessageHandler가 작동이 안됨. android에서는 제대로 동작하는데 ios에서만 작동하지 않았다.
해결
일단 나는 postman으로 간단하게 테스트 하기 위해 Firebase Cloud Messaging API(V1)을 이용하지 않고 기존에 있던 Cloud Messaging API를 이용했다.
content-available값이 없을 경우 ios에서 setBackgroundMessageHandler가 동작하지 않음
참고
--수정버전--
header
Authorization : key=firebase서버키
Content-Type : application/json
body
{
"to":"기기의 토큰값",
"notification":{
"title" : "노티 타이틀",
"body" : "노티 바디"
},
"data" : {
"title" : "데이터 타이틀",
"body" : "데이터 바디"
},
"content_available":true
}