I am not receiving data messages to IOS device on background and killed state.
See original GitHub issueHi, I am not receiving data messages in some cases to the IOS device. My server sends data messages with content_available:“true”. My expected results when an notification arrived are :
- Save the data
- Present a tray notification if the app is in one of the 3 states: killed, background, foreground but not in the right screen.
My actual results are:
- When the app is killed the notification never arrives or presented.
- When the app is in background : the first 9 notifications arrives and presented as expected, then the next notifications are not presented , but when i open the last one that was sent id presented. If I wait about 30 minutes in background state , I can receive again just 9 notifications.
- When the app is in foreground the notifications arrives and presented as expected
- Sometimes I get twice or even 4 times the same notification.
Here is my code:
import FCM, { FCMEvent,
NotificationType,
WillPresentNotificationResult,
RemoteNotificationResult } from 'react-native-fcm';
import { Platform,AppState} from 'react-native';
import deviceLog from 'react-native-device-log'
import AnalyticsUtil from '@helpers/AnalyticsHelper';
import {
PUSH_TYPE_CHAT_MESSAGE,
PUSH_TYPE_CHAT_INVITATION,
PUSH_TYPE_CHAT_INVITATION_APPROVED
} from '@helpers/Constants';
import NavigationService from './NavigationService';
import Server from './Server'
import Storage from './RealmStorage';
import Users from './Users';
const FCM_ENABLED=true;
class FCMHelper {
async setBadge(badge)
{
await FCM.setBadgeNumber(badge)
}
async resetBadge()
{
await FCM.setBadgeNumber(0);
}
async claculateBadge(count)
{
await FCM.setBadgeNumber(badge);
}
async getToken()
{
if(!this.enabled)
{
console.warn('FCM disabled')
return null;
}
let token = await FCM.getFCMToken();
return token;
}
registerToToken(callback)
{
if(!this.enabled)
{
console.warn('FCM disabled')
return null;
}
FCM.on(FCMEvent.RefreshToken, token => {
callback(token);
});
}
registerToNotification(isChatOpen,loadMessages,loadChats,loadChatRequests,isChatRequestsOpen)
{
this.isChatOpen =isChatOpen;
this.loadMessages=loadMessages;
this.loadChats=loadChats;
this.loadChatRequests=loadChatRequests;
this.isChatRequestsOpen=isChatRequestsOpen;
}
async initFCM() {
deviceLog.log("init fcm");
try
{
let result = await FCM.requestPermissions({badge: true, sound: true, alert: true});
console.log("FCM.requestPermissions result",result)
FCM.enableDirectChannel();
let token = await FCM.getFCMToken();
FCM.getInitialNotification().then(notif => {
console.log("INITIAL NOTIFICATION", notif);
});
FCM.on(FCMEvent.Notification, this.handleNotification);
FCM.on(FCMEvent.RefreshToken, token => {
console.log("fcm refresh token",token)
this.refreshToken(token);
});
FCM.on(FCMEvent.DirectChannelConnectionChanged, (data) => {
console.log('direct channel connected:' , data);
});
setTimeout(function() {
FCM.isDirectChannelEstablished().then(d => console.log('isDirectChannelEstablished:',d));
}, 1000);
this.enabled=true;
console.info('FCM succed','token:',token)
return token;
} catch(e)
{
console.warn('FCM failed',e)
this.enabled=false;
return null;
}
}
handleNotification= async (notif)=>
{
deviceLog.log('notification: t:'+notif.type +' nt:'+notif._notificationType,'Appstate:'+AppState.currentState,notif)
console.log('new notification. Appstate: ',AppState.currentState,' notification: ',notif)
switch (notif._notificationType) {
case NotificationType.Remote:
/*const PUSH_TYPE_CHAT_MESSAGE = "chat_message";
const PUSH_TYPE_CHAT_INVITATION = "invitation";
const PUSH_TYPE_CHAT_INVITATION_APPROVED = "chat_invitation_approved";*/
let event=invitation=inviting=titleText=subtitleText=null;
switch (notif.type)
{
case PUSH_TYPE_CHAT_MESSAGE:
//save message
let message= JSON.parse(notif.message);
let {author,chat,text}= message;
let chatOpen =this.isChatOpen(chat)
await Storage.insertChatMessage(chat,author,text,!chatOpen);
// findout navigation screen compare to 'ChatDetails' and props.chatId == chatid
await this.loadChats(true);
if (!chatOpen){
FCM.presentLocalNotification({
title: "New Message:" + notif.author_name,
body: notif.text,
show_in_foreground: true,
data:{
chat,
type: PUSH_TYPE_CHAT_MESSAGE,
author
},
sound: "default",
//badge:
})
}
else{
await this.loadMessages(chat,true);
}
notif.finish(RemoteNotificationResult.NewData);
break;
case PUSH_TYPE_CHAT_INVITATION:
let chatRequestsOpen =this.isChatRequestsOpen()
invitation= JSON.parse(notif.invitation);
event = invitation.event;
inviting= invitation.inviting;
titleText = "New chat invitation";
subtitleText = "from " + inviting.name;
if (event && event != "null") {
subtitleText+= "\nabout " + event;
}
await this.loadChatRequests();
if (!chatRequestsOpen){
FCM.presentLocalNotification({
title: titleText,
body: subtitleText,
show_in_foreground: true,
data:{
chat:invitation.id,
author:inviting.id,
type: PUSH_TYPE_CHAT_INVITATION
},
sound: "default",
//badge:
})
}
notif.finish(RemoteNotificationResult.NewData);
break;
case PUSH_TYPE_CHAT_INVITATION_APPROVED:
invitation= JSON.parse(notif.invitation);
event = invitation.event;
let chatId= parseInt(notif.chatId)
let approvedBy= parseInt(notif.approving_by);
titleText = "New available chat with";
let user = await Users.fetchUsers([approvedBy],true);
user =user[0];
let name = user.name;
subtitleText = name?name+" ":"";
subtitleText= subtitleText+ "wants to talk to you";
if (event && event != "null") {
subtitleText+= " about " + event;
}
await Storage.insertChatMessage(chatId,approvedBy,subtitleText,true,true);
// findout navigation screen compare to 'ChatDetails' and props.chatId == chatid
await this.loadChats(true);
FCM.presentLocalNotification({
title: titleText,
body: subtitleText,
show_in_foreground: true,
data:{
chat:chatId,
author:approvedBy,
type: PUSH_TYPE_CHAT_INVITATION_APPROVED
},
sound: "default",
//badge:
})
break;
default:
break;
}
break;
case NotificationType.WillPresent:
//do nothing
notif.finish(WillPresentNotificationResult.ALL); //other types available: WillPresentNotificationResult.None
break;
case NotificationType.NotificationResponse:
switch (notif.data.type)
{
case PUSH_TYPE_CHAT_MESSAGE:
case PUSH_TYPE_CHAT_INVITATION_APPROVED:
//navigate to chat
let {author,chat} =notif.data;
let user = await Users.fetchUsers([author],true);
user =user[0];
let thumbUrl = Users.getThumbUrl(user)
let name = user.name
let notifType = notif.data.type==="chat_message"?"Chat Message":"Chat Request Approved";
AnalyticsUtil.recordEvent("Notification - "+notifType);
NavigationService.navigate('ChatDetails', { name,thumbUrl,chatId:chat });
notif.finish();
break;
case PUSH_TYPE_CHAT_INVITATION:
AnalyticsUtil.recordEvent("Notification - Chat Request");
NavigationService.navigate('ChatRequests');
notif.finish();
break;
default:
notif.finish();
break;
}
default:
notif.finish();
break;
}
}
async refreshToken(token)
{
deviceLog.log("refresh fcm token");
if(!this.enabled)
{
console.warn('FCM disabled')
return;
}
token = token||await this.getToken();
Server.updateFCMToken(token);
}
}
const fCMHelper = new FCMHelper();
export default fCMHelper;
And here is an example of the notification received from the server:
{
"to": ".....",
"content_available":true,
"priority":"high",
"show_in_foreground": true,
"data": {
"alert": "Chat Message",
"id": 12234,
"title": "title",
"subtitle": "subtitle",
"chat_id":222,
"author_id": 333,
"author_name": "Elad Cohen",
"text": "text",
"type": "chat_message",
"message": {"author":111,"chat":22,"created":null,"id":null,"text":"text"}
}
}
Thanks Elad
Issue Analytics
- State:
- Created 5 years ago
- Comments:5 (2 by maintainers)
Top Results From Across the Web
App does not launch by data FCM | Apple Developer Forums
Hi all,. We used to launch our app in background by a silent FCM push and the app will display a local notification...
Read more >FCM Swift - Application does not receive message data in ...
It would seem that my application does not receive a message (notification or data) in background. The application can receive messages ( ...
Read more >iOS Push Notifications not received when app is terminated ...
From the answers of this post IOS data notifications with FCM, Data messages can't be received in iOS if the app is killed....
Read more >Notifications Not Shown - Mobile Push
When an app is in a Force Stopped / Force Killed state most events including FCM messages for push notifications will not be...
Read more >iOS Troubleshooting - Airship Docs
Apple reserves the right to not wake up your application when a background notification is received in order to maximize the devices battery...
Read more >Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start FreeTop Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Top GitHub Comments
for iOS, when notification arrives with
content_available:true
, it will wake JS and callbacks will be executed if they are not registered in a component. however, if user force kill the app, there is no way to run logic until app is opened by user again. system limit@evollu thank you for an incredible library. Ive benefited so much. Of note, using firebase to send push notifications I had to leave out
content_available
entirely to avoid errors. upon removal everything was working great. I needed it to allow people to reply to messages from the notification tray (iOS). I run a database save (it is a promise). This works even if the app is killed in my experience. Again, many thanks. If needed i hope to contribute my thanks with code as well. such a good library.