twilio / voice-quickstart-android

Quickstart app for the Voice Android SDK
https://www.twilio.com/docs/api/voice-sdk/android/getting-started
MIT License
187 stars 141 forks source link

Push notifications time_to_live period #201

Closed epetrenko closed 4 years ago

epetrenko commented 6 years ago

Hi there.

I have the following case. I show notifications for incoming calls. But when application isn't launched, or device is offline (or switched off), FCM can't deliver push notifications and stores it to send later (within time_to_live period, which is 4 weeks by default) once application is launched again. Therefore, when application is back it receiving outdated notifications about incoming calls which are actual only during incoming call.

Actually I'm not sure that this is the correct place to ask such question cause as far as I know this should be done on the server side, but is there a way to configure time_to_live parameter for FCM pushes? If no, then should I handle this on my end somehow?

kbagchiGWC commented 6 years ago

@epetrenko Unfortunately, making TTL configurable is not in our roadmap at this moment. You have to handle this on the application side. The payload received for incoming call and incoming call cancel look like the following. You can check the google.sent_time field to build your application logic.

Incoming call bundle :

{twi_account_sid=AC***, 
google.sent_time=1537206698263, 
google.ttl=2419200, 
twi_to=client:bob, 
twi_bridge_token=****, 
twi_message_type=twilio.voice.call, 
twi_call_sid=CA***, 
from=caller_id, 
google.message_id=0:1537206698269264%44bd9e35f9fd7ecd, 
google.priority=high, 
twi_message_id=RU3****, 
twi_from=client:alice}]

Incoming call cancel bundle :

Bundle[{twi_account_sid=AC***, 
google.sent_time=1537206734220, 
google.ttl=2419200, 
twi_to=client:bob, 
twi_message_type=twilio.voice.cancel, 
twi_call_sid=CA***, 
from=caller_id, 
google.message_id=0:1537206734224202%44bd9e35f9fd7ecd, 
google.priority=high, 
twi_message_id=RUe****, 
twi_from=client:alice}]
epetrenko commented 6 years ago

@kbagchiGWC Thanks for response.

Yes, google.sent_time is exactly thing which I tried to use. There are another issues with this cause it provides server timestamp (there could be a difference between server and client time, especially if client time is wrong). Therefore it doesn't solve original issue. For example, my device was off for a 2 hours. I received incoming call during this time. When device is back, I receive unnecessary incoming call (which actually was 2 hours ago).

Then I'll be trying to solve this by another approach.

fangzhzh commented 5 years ago

@epetrenko A little of off-topic, according to this link: https://developer.android.com/training/monitoring-device-state/doze-standby

FCM is optimized to work with Doze and App Standby idle modes by means of high-priority FCM messages. FCM high-priority messages let you reliably wake your app to access the network, even if the user’s device is in Doze or the app is in App Standby mode.

I think twilio send high priority FCM message, and should wake up app even if "application isn't launched", am I right?

kbagchiGWC commented 5 years ago

@fangzhzh Twilio always sends high-priority FCM messages. It should wake up app if it is in Doze and App Standby mode. Can you elaborate on what you mean by "if "application isn't launched"?

I have tested our test app with Doze and App Standby as suggested in https://developer.android.com/training/monitoring-device-state/doze-standby and it works as expected. Can you do the same and let me know your findings?

epetrenko commented 5 years ago

@fangzhzh If you do mean application stopped (for example, stopped via device settings), then in this case notifications won't be shown at all. Also there is another issue with Chinese devices with custom ROM. Removing app from the list of recent apps equals to stopping from device settings and in this case notifications won't be handled as well. Application should be in whitelist to avoid such behavior. And basically vendors add the most popular applications there (like WhatsApp or Gmail).

What's regarding original issue, I decided to use time from NTP servers as single source of truth to compare with google.sent_time and check if notification still actual. There is a good android library for tris purpose - TrueTime.

fangzhzh commented 5 years ago

@kbagchiGWC I tested the Doze and App Standby following the instructions, it works as expected as well.

but just as @epetrenko said, when the app is stopped via force stopped, swapped from recent in some ROMs, system received notifications and will not wake up apps.

I found another interesting scenario. Based on my test device, Samsung Galaxy S7, if the app is not in foreground for a while, logcat shows I/ActivityManager: Killing 18067:cradle.android.io.cradle.debug/u0a381 (adj 900): stop cradle.android.io.cradle.debug,MARs #2.

It looks like some devices will kill apps when the app is not in foreground for a while in order to save battery. In this case, the app is in Stopped status just like be force killed from setting.

But if the app is whitelisted for Battery Optimizations exceptions, system will not kill app.

Some famous apps are build-in whiltelist such as whatsapp, wechat, Allo, etc.

kbagchiGWC commented 4 years ago

@epetrenko

We have added notification expiration with our 5.0 release to prevent newly available devices from being notified of out-of-date calls. The original issue reported here should not be an issue anymore.

Please use the latest version and let me know if you have any additional questions.

Thank you,

-Kumkum