推送通知操作按钮不显示 - 背景和终止状态 - React Native
Posted
技术标签:
【中文标题】推送通知操作按钮不显示 - 背景和终止状态 - React Native【英文标题】:Push Notification Action Button Not Displaying - Background and Kill State - React Native 【发布时间】:2021-09-19 11:03:52 【问题描述】:我已经使用 Firebase 和 react-native-push-notification 包实现了 Firebase 推送通知。
目前,我已经根据每个推送通知的click_action实现了动作按钮。一旦应用程序处于前台,它就可以工作,并且一旦应用程序处于终止状态或后台操作按钮不显示。
我的 FCM 帮助文件
class FCMServiceHelper
register = (onRegister, onNotification, onOpenNotification) =>
this.checkPermission(onRegister);
this.createNotificationListeners(
onRegister,
onNotification,
onOpenNotification,
);
;
registerAppWithFCM = async () =>
if (Platform.OS === 'ios')
await messaging().registerDeviceForRemoteMessages();
await messaging().setAutoInitEnabled(true);
;
checkPermission = (onRegister) =>
messaging()
.hasPermission()
.then((enabled) =>
if (enabled)
// User has permissions
this.deleteToken()
this.getToken(onRegister);
else
// User doesn't have permission
this.requestPermission(onRegister);
)
.catch((error) =>
console.log('[FCMService] Permission rejected ', error);
);
;
getToken = (onRegister) =>
messaging()
.getToken(undefined,'*')
.then((fcmToken) =>
if (fcmToken)
onRegister(fcmToken);
else
console.log('[FCMService] User does not have a device token');
)
.catch((error) =>
console.log('[FCMService] getToken rejected ', error);
);
;
requestPermission = (onRegister) =>
messaging()
.requestPermission()
.then(() =>
this.deleteToken()
this.getToken(onRegister);
)
.catch((error) =>
console.log('[FCMService] Request Permission rejected ', error);
);
;
deleteToken = () =>
console.log('[FCMService] deleteToken ');
messaging()
.deleteToken(undefined,'*')
.catch((error) =>
console.log('[FCMService] Delete token error ', error);
);
;
unregisterDeviceFromNotifications = () =>
console.log('[FCMService] unreg ');
messaging()
.unregisterDeviceForRemoteMessages()
.catch((error) =>
console.log('[FCMService] Unreg device ', error);
);
;
createNotificationListeners = (
onRegister,
onNotification,
onOpenNotification,
) =>
// When the application is running, but in the background
messaging().onNotificationOpenedApp((remoteMessage) =>
console.log(
'[FCMService] onNotificationOpenedApp Notification caused app to open from background state:',
remoteMessage,
);
if (remoteMessage)
let notification = null;
let data = remoteMessage.data;
let openFromKilling = "checked" : true
notification = remoteMessage.notification;
notification.data = data;
notification.checking = openFromKilling;
onOpenNotification(notification);
);
// When the application is opened from a quit state.
messaging()
.getInitialNotification()
.then((remoteMessage) =>
console.log(
'[FCMService] getInitialNotification Notification caused app to open from quit state:',
remoteMessage,
);
if (remoteMessage)
let notification = null;
let data = remoteMessage.data;
let openFromKilling = "checked" : true
notification = remoteMessage.notification;
notification.data = data;
notification.checking = openFromKilling;
onOpenNotification(notification);
);
// Foreground state messages
this.messageListener = messaging().onMessage(async (remoteMessage) =>
console.log(
'[FCMService] A new FCM message arrived! foreground',
remoteMessage,
);
if (remoteMessage)
let notification = null;
let data = remoteMessage.data;
if (Platform.OS === 'ios')
notification = remoteMessage.notification;
else
notification = remoteMessage.notification;
notification.data = data;
onNotification(notification);
// onOpenNotification(remoteMessage.data);
);
// Triggered when have new token
// messaging().onTokenRefresh((fcmToken) =>
// alert('REFRESH TOKEN');
// console.log('[FCMService] New token refresh: ', fcmToken);
// onRegister(fcmToken);
// );
;
unRegister = () =>
// if(this.messageListener)
this.messageListener();
//
;
我的通知处理程序文件
fcmService.registerAppWithFCM();
fcmService.register(onRegister, onNotification, onOpenNotificaion , onAction);
localNotificationService.configure(onOpenNotificaion,onAction);
function onRegister(token)
saveFCMToken(token);
if (Platform.OS == 'android')
localNotificationService.createChannelAndroid('wapp');
function onNotification(notify)
var RandomNumber = Math.floor(Math.random() * 100) + 1;
let actionData = [];
if(Platform.OS == 'android')
if(notify.data.click_action == 'alert_dashboard')
actionData = ["Update contact number"]
else if(notify.data.click_action == 'account_edit')
actionData = ["Update Email"]
const options =
soundName: 'default',
playSound: true,
;
localNotificationService.showNotification(
RandomNumber,
notify.title,
Platform.OS == 'android' ? notify.body : notify.body,
notify,
options,
'wapp',
actionData
);
function onAction(notification)
console.log ('Notification action received:');
console.log(notification.action);
console.log(notification);
通知帮助文件
class NotificationHelper
configure = (onOpenNotification) =>
PushNotification.configure(
onRegister: function (token)
console.log('[NotificationManager] onRegister token:', token.token);
,
onNotification: function (notification)
console.log('[NotificationManager] onNotification:', notification);
if (Platform.OS === 'ios')
if (notification.data.openedInForeground)
notification.userInteraction = true;
if (notification.userInteraction)
onOpenNotification(notification);
else
onNotification(notification);
if (Platform.OS === 'android')
notification.userInteraction = true;
// Only call callback if not from foreground
if (Platform.OS === 'ios')
if (!notification.data.openedInForeground)
notification.finish('backgroundFetchResultNoData');
else
notification.finish('backgroundFetchResultNoData');
,
onAction: function (notification)
// alert(notification)
console.log("ACTION:", notification.action);
console.log("NOTIFICATION:", notification);
// notification.userInteraction = true;
// PushNotification.invokeApp(notification);
,
);
;
unregister = () =>
PushNotification.unregister();
;
createChannelAndroid = (channel) =>
PushNotification.createChannel(
channelId: channel, // (required)
channelName: 'My channel', // (required)
channelDescription: 'A channel to categorise your notifications', // (optional) default: undefined.
playSound: false, // (optional) default: true
soundName: 'default', // (optional) See `soundName` parameter of `localNotification` function
importance: 4, // (optional) default: 4. Int value of the Android notification importance
vibrate: true, // (optional) default: true. Creates the default vibration patten if true.
,
(created) => console.log(`createChannel returned '$created'`), // (optional) callback returns whether the channel was created, false means it already existed.
);
;
showNotification = (id, title, message, data = , options = , channel , testData) =>
PushNotification.localNotification(
/* Android Only Properties */
...this.buildAndroidNotification(
id,
title,
message,
data,
options,
channel,
testData
),
/* iOS and Android properties */
...this.buildIOSNotification(id, title, message, data, options),
/* iOS and Android properties */
title: title || '',
message: message || '',
playSound: options.playSound || true,
soundName: options.soundName || 'default',
userInteraction: true, // BOOLEAN: If the notification was opened by the user from the notification area or not
);
;
buildAndroidNotification = (
id,
title,
message,
data = ,
options = ,
channel,
testData
) =>
console.log('TEST DATA -> ',data)
return
showWhen: true, // This is probably not needed, since default value is TRUE.
when: new Date().getTime(),
group: "wapp",
groupSummary: true,
channelId: channel,
id: id,
autoCancel: true,
largeIcon: options.largeIcon || 'ic_launcher',
smallIcon: options.smallIcon || 'ic_launcher',
bigText: message || '',
subText: title || '',
vibrate: options.vibrate || true,
vibration: options.vibration || 300,
priority: options.priority || 'high',
importance: options.importance || 'high', // (optional) set notification importance, default: high,
data: data,
actions:testData,
// invokeApp:false,
;
;
buildIOSNotification = (id, title, message, data = , options = ) =>
return
alertAction: options.alertAction || 'view',
alertBody: message || '',
category: options.category || '',
userInfo:
id: id,
item: data,
,
;
;
cancelAllLocalNotifications = () =>
if (Platform.OS === 'ios')
PushNotificationIOS.removeAllDeliveredNotifications();
else
PushNotification.cancelAllLocalNotifications();
;
removeDeliveredNotificationByID = (notificationId) =>
console.log(
'[LocalNotificationService] removeDeliveredNotificationByID: ',
notificationId,
);
PushNotification.cancelLocalNotifications(id: `$notificationId`);
;
我的应用 index.js 文件
/**
* @format
*/
import React from 'react';
import 'react-native-gesture-handler';
import AppRegistry, LogBox, YellowBox from 'react-native';
import App from './app/Entrypoint';
import name as appName from './app.json';
import enableScreens from 'react-native-screens';
import messaging from '@react-native-firebase/messaging';
import backgroundGeo, checkLocationLogics from './app/helpers/backgroundLocationTracking';
import env from 'react-native-config';
enableScreens();
messaging().setBackgroundMessageHandler(async (remoteMessage) =>
console.log('Message handled in the background!', remoteMessage);
);
function HeadlessCheck( isHeadless )
if (isHeadless)
// App has been launched in the background by iOS, ignore
return null;
return <App />;
AppRegistry.registerComponent(appName, () => HeadlessCheck);
【问题讨论】:
嘿,你完成了吗?您能否分享一个要点或上述文件的内容。我需要处理类似的问题 @VinayN 很遗憾没有找到任何解决方案 【参考方案1】:尝试在 setBackgroundMessageHandler 中调用 showNotification 方法,当应用程序不在前台或终止状态时调用该方法
messaging().setBackgroundMessageHandler(async (remoteMessage) =>
console.log('Message handled in the background!', remoteMessage);
const options =
soundName: 'default',
playSound: true,
;
const title, body, data = remoteMessage;
localNotificationService.showNotification(
title,
body,
data,
options,
);
【讨论】:
以上是关于推送通知操作按钮不显示 - 背景和终止状态 - React Native的主要内容,如果未能解决你的问题,请参考以下文章