从 Android 中service 详解 和Android service 启动篇之 startForegroundService 中我们知道在android 8.0 禁止启动后台服务。提出通过startForegroundService() 启动前台服务。但是必须要配合在service 中调用Service.startForeground(),不然就会出现ANR 或者crash。

ANR log 如下:

11-06 02:01:59.616  3877  3893 E ActivityManager: ANR in com.shift.phonemanager.permission.accesslog11-06 02:01:59.616  3877  3893 E ActivityManager: PID: 136911-06 02:01:59.616  3877  3893 E ActivityManager: Reason: Context.startForegroundService() did not then call Service.startForeground()11-06 02:01:59.616  3877  3893 E ActivityManager: Load: 0.0 / 0.0 / 0.011-06 02:01:59.616  3877  3893 E ActivityManager: CPU usage from 7945ms to 0ms ago (2007-11-06 02:01:51.418 to 2007-11-06 02:01:59.363):11-06 02:01:59.616  3877  3893 E ActivityManager:   60% 3877/system_server: 35% user + 25% kernel / faults: 3744 minor 6 major11-06 02:01:59.616  3877  3893 E ActivityManager:   25% 1042/com.android.launcher3: 20% user + 4.9% kernel / faults: 11190 minor 9 major11-06 02:01:59.616  3877  3893 E ActivityManager:   18% 1149/android.process.media: 13% user + 5.3% kernel / faults: 6130 minor11-06 02:01:59.616  3877  3893 E ActivityManager:   15% 1420/adbd: 3.6% user + 11% kernel / faults: 5074 minor11-06 02:01:59.616  3877  3893 E ActivityManager:   9.7% 255/logd: 2.7% user + 6.9% kernel / faults: 5 minor11-06 02:01:59.616  3877  3893 E ActivityManager:   9.2% 3814/surfaceflinger: 4.4% user + 4.8% kernel / faults: 658 minor

 

crash log 如下:

--------- beginning of crash11-06 02:06:05.307  3106  3106 E AndroidRuntime: FATAL EXCEPTION: main11-06 02:06:05.307  3106  3106 E AndroidRuntime: Process: com.shift.phonemanager.permission.accesslog, PID: 310611-06 02:06:05.307  3106  3106 E AndroidRuntime: android.app.RemoteServiceException: Context.startForegroundService() did not then call Service.startForeground()11-06 02:06:05.307  3106  3106 E AndroidRuntime: at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1771)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at android.os.Handler.dispatchMessage(Handler.java:106)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at android.os.Looper.loop(Looper.java:164)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at android.app.ActivityThread.main(ActivityThread.java:6518)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at java.lang.reflect.Method.invoke(Native Method)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)11-06 02:06:05.307  3106  3106 E AndroidRuntime: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)11-06 02:06:05.320  3118  3118 D ExtensionsFactory: No custom extensions.

 

实例:

    private void showNotification() {        // In this sample, we'll use the same text for the ticker and the expanded notification        CharSequence text = getText(R.string.local_service_started);        // The PendingIntent to launch our activity if the user selects this notification        PendingIntent contentIntent = PendingIntent.getActivity(this, 0,                new Intent(this, LocalServiceActivities.Controller.class), 0);        // Set the info for the views that show in the notification panel.        Notification notification = new Notification.Builder(this)                .setSmallIcon(R.drawable.stat_sample)  // the status icon                .setTicker(text)  // the status text                .setWhen(System.currentTimeMillis())  // the time stamp                .setContentTitle(getText(R.string.local_service_label))  // the label of the entry                .setContentText(text)  // the contents of the entry                .setContentIntent(contentIntent)  // The intent to send when the entry is clicked                .build();        // Send the notification.        mNM.notify(NOTIFICATION, notification);    }

 

实例:

    private void setForegroundNotification() {        NotificationManager nm = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);        String channelId = "access_log_channel";        NotificationChannel channel = new NotificationChannel(channelId, "channel_1",                NotificationManager.IMPORTANCE_DEFAULT);        nm.createNotificationChannel(channel);        Notification notification = new Notification.Builder(this).setChannelId(channelId)                .setSmallIcon(R.drawable.ic_launcher)                .setContentTitle(getString(R.string.permission_access_log_title))                .build();        startForeground(1, notification);    }

 

 

参考:

https://developer.android.com/about/versions/oreo/background

https://developer.android.com/reference/android/app/Service

 

更多相关文章

  1. 基于Service与ContentProvider的音乐播放实例
  2. Android中使用putExtra()传递对象实例
  3. android创建aidl小实例
  4. Android 需要使用不同实例的情况
  5. Android唤醒、解锁屏幕代码实例
  6. Android中从图库中选取图片实例详解
  7. Android中ExpandableListView的用法实例
  8. android用户界面之Notification教程实例汇总
  9. Android监听Home键实例详解

随机推荐

  1. Android 两级都带CheckBox的 ExpandableL
  2. 移动数据流程
  3. android的sqlite使用
  4. Android核心模块内容概述 2012.07.25
  5. Android 2.3.3 SDK 源代码关联Eclipse
  6. 源码分析Android启动流程
  7. Android_AndroidManifest.xml
  8. Android Studio开发笔记
  9. 2014.07.23(2) ——— android FragmentPag
  10. 【Android开发学习08】SurfaceView显示动