expo: expo-notifications scheduleNotification is not working as expected in devices

🐛 Bug Report

STACK OVERFLOW QUESTION

Summary of Issue

Im im trying to schedule a repeat notification on everyday morning 9AM & night 9PM everyday. One Everytime use user opens app, im cancelling all old notifications & scheduling new one, (tried with checking scheduled notification, if not exist schedule new). This seems to be working fine in android simulator, when i install app in phone it triggers notification very rarely or some times nothing for a week. I have just followed given documentation for repeat local notifications. Need help…

Environment - output of expo diagnostics & the platform(s) you’re targeting

 Expo CLI 3.27.14 environment info:
    System:
      OS: macOS 10.15.7
      Shell: 5.7.1 - /bin/zsh
    Binaries:
      Node: 12.18.3 - /usr/local/bin/node
      Yarn: 1.22.4 - /usr/local/bin/yarn
      npm: 6.14.6 - /usr/local/bin/npm
      Watchman: 4.9.0 - /usr/local/bin/watchman
    Managers:
      CocoaPods: 1.9.3 - /usr/local/bin/pod
    SDKs:
      iOS SDK:
        Platforms: iOS 13.7, DriverKit 19.0, macOS 10.15, tvOS 13.4, watchOS 6.2
      Android SDK:
        API Levels: 23, 28, 29
        Build Tools: 28.0.3, 29.0.2, 29.0.3, 30.0.0
        System Images: android-26 | Google APIs Intel x86 Atom, android-29 | Google APIs Intel x86 Atom
    IDEs:
      Android Studio: 4.0 AI-193.6911.18.40.6626763
      Xcode: 11.7/11E801a - /usr/bin/xcodebuild
    npmPackages:
      expo: ^39.0.0 => 39.0.2 
      react: 16.13.1 => 16.13.1 
      react-dom: 16.13.1 => 16.13.1 
      react-native: 0.63.2 => 0.63.2 
      react-native-web: ~0.13.7 => 0.13.13 
    npmGlobalPackages:
      expo-cli: 3.27.14
    Expo Workflow: bare 

Reproducible Demo

const scheduleNotifications = async () =>{
// Cancel All notifications
await Notifications.cancelAllScheduledNotificationsAsync();
//9AM notification
        await Notifications.scheduleNotificationAsync({
            identifier: 'morning-1',
            content: {
                title: `Good Morning!`,
                subtitle: 'Greetings',
                body: `Have a great day`,
                sound: true,
                color: "#ffffff",
                data: {
                    to: 'new-log'
                }
            },
            trigger: {
                hour: 9,
                minute: 0,
                repeats: true
            }
        });
    

   //9PM notification
    await Notifications.scheduleNotificationAsync({
                identifier: 'night-notification',
                content: {
                    title: `Good Night :)`,
                    subtitle: 'Have a great sleep :D',
                    body: `Have a great sleep :D`,
                    sound: true,
                    data: {
                        to: 'new-log'
                    },
                    color: "#000000"                },
                trigger: {
                    hour: 21,
                    minute: 0,
                    repeats: true
                }
            });
}

Steps to Reproduce

  • Cancel all old notifications
  • scheduling 2 daily notifications with triggers
 trigger: {
                hour: 9,
                minute: 0,
                repeats: true
            }

&

 trigger: {
                    hour: 21,
                    minute: 0,
                    repeats: true
                }
  • wait for thenotification

Expected Behavior vs Actual Behavior

Expected It should trigger 2 notifications every day, 1 on 9 AM & 1 on 9 PM Actual Triggering notifications regardless of trigger time & day, some tomes 3 days once, some day all 2 together at night, sometimes nothing for a week.

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Comments: 24 (6 by maintainers)

Most upvoted comments

If someone is struggling with the same issue : for me the solution was to upgrade my expo SDK from 38 to 39. I think it is supposed to be working with 38 version but for some reason it doesn’t. As soon as I upgraded it starts working like a charm.

hi @ltsharma, it sounds like maybe your scheduled notifications are getting a little mixed up. What you may want to do is build in some sort of debugging workflow where you can check on what notifications you have scheduled with Notifications.getAllScheduledNotificationsAsync. I’ve tested daily notification triggers myself, e.g.

await Notifications.scheduleNotificationAsync({
      identifier: "myidentifer",
      content: {
        title: "You've got mail! 📬",
        body: "Here is the notification body",
        data: { data: "goes here" },
      },
      trigger: {
        hour: 12,
        minute: 15,
        repeats: true,
      },
    });

and haven’t seen any of the behavior you’re describing

Finally, yes. if battery optimization is turned on in xaomi & onplus devices were not getting local daily notifications. i turned it off in app setting now its working properly. so my next questions,

  • is it expected behavior?
  • if yes, how to disable it by default? (i got soln, but that will scares user about battery optimization by showing it in model while allowing it).
  • if No, how to solve it?

Yep of course 😃 You can find bellow a simple component example to create a notification from what i did. I didn’t try it but it should work, tell me if not :

First => don’t forget to add this line in your app.json under the android object : "useNextNotificationsApi": true,

Then : ` import * as Notifications from ‘expo-notifications’; import * as Permissions from ‘expo-permissions’;

   // don't forget this notificationHandler
   Notifications.setNotificationHandler({
    handleNotification: async () => ({
       shouldShowAlert: true,
       shouldPlaySound: false,
       shouldSetBadge: false,
    }),
 });

 class Notification extends React.Component {
  constructor(props) {
    super(props)
    this.state = {
        time: Date.now(), // change it by the time you need
        title: 'title',
        body: 'content'
     }
 }

async componentDidMount() {
    const { status: existingStatus } = await Permissions.getAsync(Permissions.NOTIFICATIONS);
    let finalStatus = existingStatus;
    if (existingStatus !== 'granted') {
      const { status } = await Permissions.askAsync(Permissions.NOTIFICATIONS);
      finalStatus = status;
    }
    if (finalStatus !== 'granted') {
      alert(this.context.translate(this.context.translations, 'notification.missing_permission'));
      return;
    }
}

onSubmit() {
        Notifications.scheduleNotificationAsync({
            content: {
            title: this.state.title,
            body: this.state.body,
            },
            trigger: {
                // every day at the same time
                hour: date.getHours(),
                minute: date.getMinutes(),
                repeats: true
            }
        });
 }

render() {
    <View style={{flex: 1}}>
       <Button title="Try me" color="#841584" onPress={() => this.onSubmit()}></Button>
    </View>
}
}

`

@ltsharma : I am also using Daily and Scheduled Local Notifications and having the same problems on Android where they work when battery optimization is turned off.

Is there a better solution to this?

Will this happen even with Push Notifications as well? I found this on OneSignal website : https://documentation.onesignal.com/docs/notifications-show-successful-but-are-not-being-shown#low-power-energy-saving

@ltsharma - android device oems have full control over what they want to do to the operating system on their devices. some may make strange changes like this that impact notifications and create inconsistency in the android ecosystem because they think it will be a good feature/improvement for their customer. you could detect the device type and warn people in the case of devices that you believe have this issue, if you like.

@cruzach , it’s not actually about troubleshooting. After intensive observations, found that this behavior is happening only in custom UIs like miui (xiaomi), emui (one plus) & one UI (Samsung). Nokia appears to be working fine with pure android. Now i’m trying with disabling battery optimization off in app setting, i will update the status.