Android Oreo持续通知“应用在后台运行”

时间:2017-09-21 04:03:33

标签: android android-notifications android-8.0-oreo

我是一名Android应用开发者,正在开发即时消息应用。该应用在Android Oreo系统上存在通知问题,该系统显示持续通知“应用程序在后台运行”并且无法清除,并且在Android Oreo之前系统正常。

Screenshot: The phone shows persistent notification App is running in the background

我找到了一些讨论,例如Nexus Help Forum about this question,但它在我的手机设置中无效。

我想知道如何以编程方式隐藏此通知,该应用也可以立即接收消息,因为它是即时消息应用。

非常感谢任何帮助。

4 个答案:

答案 0 :(得分:4)

  

该应用在Android Oreo系统上存在通知问题,该系统显示持续通知“应用程序在后台运行”且无法清除,并且在Android Oreo之前系统正常。

您使用startForeground()的最低重要性Notification

  

我想知道如何以编程方式隐藏此通知

startForeground()Notification一起使用,其重要性高于最低限度。或者,不要使用startForeground()

  

我发现一些安装消息应用程序,如微信,Facebook在Android Oreo上没有这个问题

大概他们没有使用前台服务。例如,他们可能正在使用Firebase云消息传递(FCM)。

答案 1 :(得分:2)

然而,在我们讨论如何摆脱它之前,让我们首先谈谈它为什么会出现。

基本上,在Android的早期版本中,没有真正的方法可以知道应用程序是否在后台运行,并且做了一堆不应该做的事情。在大多数情况下,这些行为不当的应用程序会通过保持系统唤醒来对电池造成严重破坏 - 这些被称为“唤醒锁”。在外行人看来,这是让系统无法入睡。那很糟糕。

借助奥利奥,谷歌正在呼吁开发人员让他们的应用程序通过新通知执行此类操作。基本上,如果一个应用程序在后台运行并且缩短了电池续航时间,这个新通知会告诉你。

注意:有一些合法的场景,应用程序将在后台持续运行,例如运行的VPN服务。但是,通常,应用程序在后台运行不合理。

值得注意的是,删除通知并不能解决问题。期。这个通知存在的原因是什么,摆脱它通知无法解决根本问题。您需要更改应用程序中的设置或完全卸载它。

只要您理解并且仍想删除它,就让我们做这件事。 因为这是一个相对关键的系统设置,所以Oreo本身无法将其删除。这是有道理的。

但与大多数事情一样,开发者社区已找到一种方法将其删除,开发人员iboalali发布了一个应用程序来做到这一点。它实际上只是被称为“隐藏”在后台运行'通知',这就像应用程序名称一样简单。来吧,安装它。

没有root,就没有办法真正阻止Android系统在Android 8.0 Oreo中显示持久的“应用程序在后台运行”通知。查看ForegroundServiceController的源代码,它的实现和ForegroundServiceDialog并没有真正揭示我们可以利用的任何东西。到目前为止,没有找到任何结果。

Here's a Blog post that can help you

答案 2 :(得分:1)

首先,您必须具有 NotificationListenerService 实现。其次,在此服务中(在onListenerConnected回调之后),使用名为“ android”的packageName检查活动正在进行的通知。并检查此通知的标题是您的应用名称或文本值是否是“应用在后台运行”并暂停。

public class NLService extends NotificationListenerService {

   @Override
   public void onNotificationRemoved(StatusBarNotification sbn) {}

   @Override
   public void onListenerConnected() {
      super.onListenerConnected();

      checkOngoingNotification();
   }

   @Override
   public void onNotificationPosted(StatusBarNotification sbn){

      if(sbn.isOngoing()) { 

         checkOngoingNotification(); 
         return; 
      }
   }

   private void checkOngoingNotification() {

      StatusBarNotification[] activeNotifications = getActiveNotifications();

      Log.i("NLService", "Active notifications size : " + activeNotifications.length);

      for (StatusBarNotification statusBarNotification : activeNotifications) {

         Log.i("NLService", "notification package  : " + statusBarNotification.getPackageName());
         Log.i("NLService", "notification id       : " + statusBarNotification.getId());
         Log.i("NLService", "notification key      : " + statusBarNotification.getKey());
         Log.i("NLService", "isOngoing             : " + statusBarNotification.isOngoing());
         Log.i("NLService", "isClearable           : " + statusBarNotification.isClearable());
         Log.i("NLService", "groupKey              : " + statusBarNotification.getGroupKey());

         Notification notification = statusBarNotification.getNotification();

         CharSequence title = notification.extras.getCharSequence(Notification.EXTRA_TITLE);
         CharSequence text  = notification.extras.getCharSequence(Notification.EXTRA_TEXT);


         if (title != null && text != null) {

            Log.i("NLService", "title                : " + title);
            Log.i("NLService", "text                 : " + text);


            if (statusBarNotification.getPackageName().equals("android") &&
                (title.toString().contains("Your App Name") || text.toString().contains("App is running"))) {

                long snoozLong = 60000L * 60L * 24L * 20L;

                this.snoozeNotification(statusBarNotification.getKey(), snoozLong);

                Log.i("NLService", "Snoozed notification  : " + title);
            }
        }
    }
}

答案 3 :(得分:0)

事实证明,FROM node:14.9 WORKDIR /usr/src/app COPY package*.json ./ RUN npm install COPY . . EXPOSE 3000 CMD [ "npm", "start" ] 与频道的startForeground()不仅是通知的来源之一。如果您呼叫IMPORTANCE_MIN并给它通知 startForeground(),结果将是相同的。 https://android.googlesource.com/platform/frameworks/base/+/master/services/core/java/com/android/server/am/ServiceRecord.java#816

您还可以在日志中找到类似的内容:

ActivityManager:尝试以损坏的通知(无图标)启动前台服务(ComponentInfo {com.example.app/com.example.app.ExampleService}):Notification(channel = channel_example pri = 0 contentView = null vibrate =空声音=空默认值= 0x0标志= 0x40颜色= 0x00000000 vis = PRIVATE))