Android kitkat 上未显示通知

Android notifications not showing on kitkat

我正在尝试显示来自 firebase 消息传递的通知,它适用于 oreo 及更高版本,但仅在 kitkat 设备上播放声音(我没有其他设备或模拟器可以测试)并且我收到一些奇怪的错误日志,例如

Could not find class 'android.app.Notification$Action$Builder', referenced 
from method android.support.v4.app.NotificationCompatBuilder.addAction

我真的很难确定这一点,所以这是代码的主要部分

private void sendNotification(Map<String, String> data) {

    String author = data.get("USER_NAME");
    String title = data.get("TITLE");
    String body = data.get("BODY");
    String id = data.get("USER_NUMBER");
    String message = data.get("MESSAGE");
    String type = data.get("TYPE");
    String image = data.get("IMAGE");
    String profileImage = data.get("USER_IMAGE");
    String shortMessage = "";
    Intent intent;
    Bitmap bitmap;
    Bitmap bitmap2;

    intent = new Intent(this, MessageListActivity.class);
    if (MessageListActivity.isAppRunning)
        intent = new Intent(this, MainActivity.class);

    intent.putExtra(Constants.USER_NAME, author);
    intent.putExtra(Constants.USER_NUMBER, id);
    intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
    /*
    TaskStackBuilder stackBuilder = TaskStackBuilder.create(this);
    stackBuilder.addParentStack(MainActivity.class);
    stackBuilder.addNextIntent(intent);
    */
    PendingIntent pendingIntent = PendingIntent.getActivity(this, 0 /* Request code */, intent,
            PendingIntent.FLAG_ONE_SHOT);
    /*
    String replyLabel = getString(R.string.notif_action_reply);
    RemoteInput remoteInput = new RemoteInput.Builder(KEY_REPLY)
            .setLabel(replyLabel)
            .build();
    */
    // If the message is longer than the max number of characters we want in our
    // notification, truncate it and add the unicode character for ellipsis
    if (message.length() > NOTIFICATION_MAX_CHARACTERS) {
        shortMessage = message.substring(0, NOTIFICATION_MAX_CHARACTERS) + "\u2026";
    }
    Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
    NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this);
    if (type.equals("IMAGE")) {
        bitmap = getBitmapfromUrl(image);
        bitmap2 = getBitmapfromUrl(profileImage);
        notificationBuilder
                .setLargeIcon(bitmap2)
                .setSmallIcon(R.drawable.message_me)
                .setContentTitle(String.format(getString(R.string.notification_message), author))
                .setStyle(new NotificationCompat.BigPictureStyle()
                        .setSummaryText(shortMessage)
                        .bigPicture(bitmap))
                .setContentText(message)
                .setColor(getResources().getColor(R.color.colorPrimary))
                .setAutoCancel(true)
                .setSound(defaultSoundUri)
                .setContentIntent(pendingIntent);
    } else if (type.equals("TEXT")) {
        bitmap2 = getBitmapfromUrl(profileImage);
        notificationBuilder
                .setSmallIcon(R.drawable.message_me)
                .setLargeIcon(bitmap2)
                .setContentTitle(String.format(getString(R.string.notification_message), author))
                .setStyle(new NotificationCompat.BigTextStyle()
                        .bigText(message))
                .setContentText(shortMessage)
                .setColor(getResources().getColor(R.color.colorPrimary))
                .setAutoCancel(true)
                .setSound(defaultSoundUri)
                .setContentIntent(pendingIntent);
    }
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN
            && Build.VERSION.SDK_INT < Build.VERSION_CODES.O) {
        notificationBuilder.setPriority(NotificationCompat.PRIORITY_HIGH);
        getManager().notify(0 /* ID of notification */, notificationBuilder.build());
    } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        notificationBuilder = getChannelNotification(title, body, shortMessage, SINGLE_CHANNEL_ID, pendingIntent, type, image, profileImage);
        getManager().notify(0, notificationBuilder.build());
    }
}



private NotificationManager getManager() {
    if (mManager == null) {
        mManager = (NotificationManager)getSystemService(Context.NOTIFICATION_SERVICE);
    }
    return mManager;
}

所有数据都存在并更正我从中得到的第一个错误是

 Could not find class 'android.app.NotificationChannel', referenced from 
 method com.sealstudios.aimessage.MyFirebaseMessagingService.createChannels

我的 createChannels 方法是这样

@RequiresApi(api = Build.VERSION_CODES.O)
public void createChannels() {
    // create single channel
    NotificationChannel singleChannel = new NotificationChannel(SINGLE_CHANNEL_ID,
            SINGLE_CHANNEL_NAME, NotificationManager.IMPORTANCE_DEFAULT);
    singleChannel.enableLights(true);
    singleChannel.enableVibration(true);
    singleChannel.setLightColor(R.color.colorPrimary);
    singleChannel.setLockscreenVisibility(Notification.VISIBILITY_PUBLIC);
    getManager().createNotificationChannel(singleChannel);

    // create group channel
    NotificationChannel groupChannel = new NotificationChannel(GROUP_CHANNEL_ID,
            GROUP_CHANNEL_NAME, NotificationManager.IMPORTANCE_HIGH);
    groupChannel.enableLights(true);
    groupChannel.enableVibration(true);
    groupChannel.setLightColor(R.color.colorPrimary);
    groupChannel.setLockscreenVisibility(Notification.VISIBILITY_PUBLIC);
    getManager().createNotificationChannel(groupChannel);
}

但这仅在像这样的 if 括号中从 onMessageReceived 调用

@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
    // Check if message contains a data payload.
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        createChannels();
    }
    if (remoteMessage.getData().size() > 0) {
        Map<String, String> data = remoteMessage.getData();
        if (data.size() > 0) {
            if (!(chatActive && remoteMessage.getData().get("USER_NAME").equals(senderID))) {
                //TODO add a mute notifications
                sendNotification(data);
            }
        }
    }
    // Check if message contains a notification payload.
    if (remoteMessage.getNotification() != null) {

    }
}

如前所述,我收到了完整的通知,不用担心 android 奥利奥来自一个单独的方法,就是这个

@RequiresApi(api = Build.VERSION_CODES.O)
public NotificationCompat.Builder getChannelNotification(String title, 
String body, String smallMessage, String channelId,
                                                         PendingIntent pendingIntent, String type, String largeImage,
                                                         String smallImage) {


    if (type.equals("TEXT")) {
        Bitmap smallBitmap = getBitmapfromUrl(smallImage);
        return new NotificationCompat.Builder(getApplicationContext())
                .setChannelId(channelId)
                .setContentTitle(title)
                .setStyle(new NotificationCompat.BigTextStyle().bigText(body))
                .setContentText(body)
                .setColor(getResources().getColor(R.color.colorPrimary))
                .setSmallIcon(R.drawable.message_me)
                .setLargeIcon(smallBitmap)
                .setContentIntent(pendingIntent)
                .setAutoCancel(true);
    } else if (type.equals("IMAGE")) {
        Bitmap smallBitmap = getBitmapfromUrl(smallImage);
        Bitmap largeBitmap = getBitmapfromUrl(largeImage);
        return new NotificationCompat.Builder(getApplicationContext())
                .setChannelId(channelId)
                .setContentTitle(title)
                .setStyle(new NotificationCompat.BigPictureStyle().setSummaryText(smallMessage).bigPicture(largeBitmap))
                .setContentText(body)
                .setColor(getResources().getColor(R.color.colorPrimary))
                .setSmallIcon(R.drawable.message_me)
                .setLargeIcon(smallBitmap)
                .setContentIntent(pendingIntent)
                .setAutoCancel(true);
    }
    return new NotificationCompat.Builder(getApplicationContext())
            .setChannelId(channelId)
            .setContentTitle(title)
            .setContentText(body)
            .setColor(getResources().getColor(R.color.colorPrimary))
            .setSmallIcon(R.drawable.message_me)
            .setContentIntent(pendingIntent)
            .setAutoCancel(true);
}

但除此之外,我只是收到通知声音,我确信在我将目标 sdk 提高到 27 之前它曾经有效,但我们将不胜感激

这似乎已通过更新 gradle 插件修复