java - 如果应用程序在后台,如何使用 fcm 获取从服务器发送的数据?

标签 java android firebase background firebase-cloud-messaging

我正在从服务器向我的应用程序发送 fcm 通知。

我正在从包含 user_id 的服务器发送数据。如果应用程序在前台,我将在 FirebaseMessageService 类中获取此 userId。但是当应用程序在后台时没有得到它。由于 FirebaseMessagingService 类仅在应用程序处于前台时执行。

那么当应用程序处于后台时,我该如何获取这个id呢?

    public class MyFirebaseMessagingService extends FirebaseMessagingService {

    private static final String TAG = "MyFirebaseMsgService";
    private String mUserId;
    private Boolean mUpdateNotification;

    @Override
    public void onMessageReceived(RemoteMessage remoteMessage) {
        //Displaying data in log
        //It is optional
        Log.d(TAG, "From: " + remoteMessage.getFrom());
        Log.d(TAG, "Notification Message Body: " + remoteMessage.getNotification().getBody());

        String clickAction = remoteMessage.getNotification().getClickAction();

        mUserId = remoteMessage.getData().get("user_id");

        String title = remoteMessage.getNotification().getTitle();

        //Calling method to generate notification
        sendNotification(remoteMessage.getNotification().getBody(),clickAction,title);
    }

    //This method is only generating push notification
    //It is same as we did in earlier posts
    private void sendNotification(String messageBody,String clickAction,String title) {

        mUpdateNotification = true;

        Intent intent = new Intent(clickAction);

        intent.putExtra("userId",mUserId);
        intent.putExtra("updateNotification",mUpdateNotification);

        intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent,
                PendingIntent.FLAG_ONE_SHOT);

        Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
        NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
                .setSmallIcon(R.drawable.ic_launcher)
                .setContentTitle(title)
                .setContentText(messageBody)
                .setAutoCancel(true)
                .setSound(defaultSoundUri)
                .setContentIntent(pendingIntent);

        NotificationManager notificationManager =
                (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

        notificationManager.notify(0, notificationBuilder.build());
    }
}

编辑:

我仍在使用数据负载 onMessageReceived 当应用程序处于后台时不会被调用。

 public function sendPush($text, $tokens, $apiKey,$user_id)
{

    $notification = array(
        "title" => "User updated profile.",
        "text" => $text,
        'vibrate' => 3,
        "click_action" => "OPEN_ACTIVITY_2",
        'sound' => "default",
        'user_id' => $user_id
    );

    $data = array("user_id" => $user_id);

    $msg = array
    (
        'message' => $text,
        'title' => 'User updated profile.',
        'tickerText' => 'New Message',
    );
    $fields = array
    (
        'to' => $tokens,
        'data' => $data,
        'notification' => $notification
    );

    $headers = array
    (
        'Authorization: key=' . $apiKey,
        'Content-Type: application/json'
    );

    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, 'https://android.googleapis.com/gcm/send');
    curl_setopt($ch, CURLOPT_POST, true);
    curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
    curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($fields));

    $result = curl_exec($ch);
    //  echo($result);
    //    return $result;
    curl_close($ch);
}

有人可以帮忙吗?谢谢..

最佳答案

我明白了。在您的有效载荷中,您同时使用了 notificationdata 有效载荷,当应用程序处于后台时,这会更改您应该接收详细信息的位置。在doc我在评论中提到,如果两者都包含在有效负载中,您可以在摘要中看到:

Data: in extras of the intent.

更具体地说:

Handle notification messages in a backgrounded app

When your app is in the background, Android directs notification messages to the system tray. A user tap on the notification opens the app launcher by default.

This includes messages that contain both notification and data payload (and all messages sent from the Notifications console). In these cases, the notification is delivered to the device's system tray, and the data payload is delivered in the extras of the intent of your launcher Activity.

我觉得这个answer @ArthurThompson 解释得很好:

When you send a notification message with a data payload (notification and data) and the app is in the background you can retrieve the data from the extras of the intent that is launched as a result of the user tapping on the notification.

From the FCM sample which launches the MainActivity when the notification is tapped:

if (getIntent().getExtras() != null) {
    for (String key : getIntent().getExtras().keySet()) {
        String value = getIntent().getExtras().getString(key);
        Log.d(TAG, "Key: " + key + " Value: " + value);
    }
}

关于java - 如果应用程序在后台,如何使用 fcm 获取从服务器发送的数据?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40105215/

相关文章:

android - 在 Android 的 shouldInterceptRequest 中获取 webview 中的响应头

ios - Google SDK 在 Xcode 中记录两次

java - loadUserByUsername 使用 DaoAuthenticationProvider 执行两次

用于验证字符串的 Java 正则表达式?

java - 大字符串导致的 OutOfMemoryException

javascript - 如何使用javascript在firebase中将在线用户的状态更改为离线用户

javascript - Firebase 用户已登录

java - Android包组织

java - Java 有检查对象类型的方法吗?

android - 在 Android 应用程序中为蓝牙脉搏率传感器创建实时图表