guolindev/booksource

第十章最佳实践 在8.x系统上创建通知报错

qinkangdeid opened this issue · 1 comments

如题 代码在7.x系统上运行没有问题,在8.x的系统上提示一下错误,之后闪退:

I/MainActivity: onClick:start_download 
I/DownloadService: startDownload: url = http://mirror.rise.ph/eclipse/oomph/epp/2018-09/Ra/eclipse-inst-mac64.dmg
    startDownload: downloadTask == null
I/DownloadService: pre startForeground
I/DownloadTask: doInBackground:fileName {}/eclipse-inst-mac64.dmg
D/skia: --- SkAndroidCodec::NewFromStream returned null
I/Choreographer: Skipped 148 frames!  The application may be doing too much work on its main thread.
D/AndroidRuntime: Shutting down VM
E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.qinkangdeid.servicebestpractice, PID: 5938
    android.app.RemoteServiceException: Bad notification for startForeground: java.lang.RuntimeException: invalid channel for service notification: Notification(channel=null pri=0 contentView=null vibrate=null sound=null defaults=0x0 flags=0x40 color=0x00000000 vis=PRIVATE)
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1768)
        at android.os.Handler.dispatchMessage(Handler.java:106)
        at android.os.Looper.loop(Looper.java:164)
        at android.app.ActivityThread.main(ActivityThread.java:6494)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)
D/NetworkSecurityConfig: No Network Security Config specified, using platform default

应该是 Notification的写法上有改变了? 刚学习 望解答

解决了

在8.x上需指定channelId

  1. 在Service上添加channelId:
    private String NOTIFICATION_ID = "com.qinkangdeid.servicebestpractice.DownloadService";
    private String NOTIFICATION_NAME = "com.qinkangdeid.servicebestpractice.DownloadService";
   /**
     * Called by the system when the service is first created.  Do not call this method directly.
     */
    @Override
    public void onCreate() {
        super.onCreate();
        notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
        // 如果是 O 以上系统 创建NotificationChannel
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationChannel channel = new NotificationChannel(NOTIFICATION_ID, NOTIFICATION_NAME, NotificationManager.IMPORTANCE_HIGH);
            notificationManager.createNotificationChannel(channel);
        }
        startForeground(1, getNotification());
        stopForeground(true);
    }
  1. 在通知上也加上:
private Notification getNotification(String title, int progress) {
        Intent intent = new Intent(this, MainActivity.class);
        PendingIntent pi = PendingIntent.getActivity(this, 0, intent, 0);
        Notification.Builder builder = new Notification.Builder(this);
        builder.setSmallIcon(R.mipmap.ic_launcher);
        builder.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher));
        builder.setContentIntent(pi);
        builder.setContentTitle(title);


        //设置Notification的ChannelID,否则不能正常显示
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            builder.setChannelId(NOTIFICATION_ID);
        }

        if (progress >= 0) {
            // 当progress大于或等于0时才需显示下载进度
            builder.setContentText(progress + "%");
            builder.setProgress(100, progress, false);
        }
        return builder.build();
    }