2

Background: we created an app that is used for tracking your working hours, you press Check in when you arrive and Check out when you leave. We thought that it would be nice if the user could set reminders to check-in or out. As we need data about the user's current check-in state in order to display the right text, we can't just schedule the notifications, we need to fetch that data from the online database first and then decide what to display, therefore we need a WorkManager.

Sometimes one notification (time to check-in) doesn't show, despite log message about the background work being successful, and another one that was supposed to display after (time to check out) displays.

I'm using Samsung Galaxy S9+ with the latest updates (Android 9).

I tried checking scheduled jobs via ADB. Sometimes they are there with correct delays and everything, sometimes they aren't there at all, but notifications arrive anyway, so that's not all that reliable.

I went through the scheduling using debugger at every case I have covered and everything got set up exactly as I expected: the new shift is added to the array and populated with expected data, work is scheduled at the correct time. When edited, old work is canceled by UUID, a new one is created. On delete, work is canceled and the shift is set to null.

First, I need to schedule the work for a specific shift. Shift has attributes shiftFrom, shiftTo and UUIDs of scheduled notifications for those times. In order to schedule the workers, I have a NotificationScheduler class with scheduleWeekly method in which I determine the delays and then I schedule the work:

val sendNotificationRequest = PeriodicWorkRequestBuilder<NotificationsWorker>(7, TimeUnit.DAYS)
                .setInputData(
                    workDataOf(
                        NotificationsWorker.TITLE_PARAM to title,
                        NotificationsWorker.CONTENT_PARAM to content,
                        NotificationsWorker.ACTION to action // this tells the worker wheter the user is supposed to check in or check out when it's triggered
                    )
                )
                .setInitialDelay(initialDelayMinutes, TimeUnit.MINUTES) // wanted time - current time converted to minutes
                .build()

            WorkManager.getInstance(context).enqueue(sendNotificationRequest)

When triggered, it calls NotificationsWorker. Based on the current check-in state and whether the user is supposed to check-in or out I decide which text I'm going to display in the notification. Also, the log message created by me is logged - the work indeed is triggered at the correct time.

Then I send a notification using this method:

private fun sendNotification(title: String, content: String) {
        val notificationIntent = Intent(context, SplashActivity::class.java) // for when the notification is clicked

        notificationIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP or Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK)

        val intent = PendingIntent.getActivity(
            context, 0,
            notificationIntent, 0
        )

        val builder =
            NotificationCompat.Builder(context, NOTIFICATION_CHANNEL_ID)
                .setSmallIcon(package.appname.R.drawable.ic_app_icon)
                .setContentTitle(title)
                .setContentText(content)
                .setContentIntent(intent)
                .setAutoCancel(true)
                .setStyle(NotificationCompat.BigTextStyle().bigText(content))
                .setPriority(NotificationCompat.PRIORITY_DEFAULT)

        with(NotificationManagerCompat.from(context)) {
            notify(0, builder.build())
        }
    }

What I expect is for notifications to arrive +-10 minutes from when they were scheduled and mostly that is what happens, but sometimes they don't arrive at all and sometimes I get them at really weird times (for example, I got one saying I was supposed to check-in at 22:12 on Saturday, but the shifts were scheduled 8-16, Monday to Friday).

Also, the mentioned notification on Saturday somehow managed to acquire data about my check-in the state, but I had no internet connection and currently notifications receive no local data whatsoever.

Muneeb Ali
  • 472
  • 6
  • 14
Filip Pranklin
  • 345
  • 1
  • 3
  • 14
  • Only thing I see is a constant notification ID - if only one notification is shown at all that's fine though, otherwise this could be the source of missing notifications even if the workers run correctly. Do I understand you correctly, your worker's `doWork` function is called at correct times (checked with logs) and you do create the notifications inside this function but those notifications do not show up reliably? – prom85 Aug 26 '19 at 12:09
  • Yes, `doWork` is called at correct times. I tried using what is proposed [here](https://stackoverflow.com/questions/25713157/generate-int-unique-id-as-android-notification-id) during initial testing and there was no difference, but I will try to put it back and see how it behaves. – Filip Pranklin Aug 26 '19 at 14:01
  • Could you tell me which devices are you testing upon i experienced that chinese ROM devices aren't supporting background task either via workmanager or service. – Bali Aug 26 '19 at 14:27
  • Update: using AtomicInteger for notification IDs didn't fix the problem. I'm using only Samsung Galaxy S9+ as it's the only device I own. – Filip Pranklin Aug 27 '19 at 07:32
  • seems there is an issue in real devices. there is no problem om the emulator – chitgoks May 29 '20 at 13:42

0 Answers0