英文:
Firebase push notification on new chat message
问题
我已经创建了一个应用程序,在其中有一个聊天功能。
我希望用户在离开应用程序时能收到新消息的通知。
为了实现这一点,我正在使用Firebase
服务。
现在,每当发送一条消息时,我调用以下方法:
我创建了以下MyFirebaseMessagingService
类来测试何时调用它:
private class MyTask extends AsyncTask<MyTaskParams, Void, Void> {
@Override
protected Void doInBackground(MyTaskParams... params) {
String userDeviceIdKey = params[0].url;
String title = params[0].title;
String body = params[0].body;
String authKey = "XXXXX"; // 你的 FCM AUTH 密钥
String FMCurl = "https://fcm.googleapis.com/fcm/send";
URL url;
try {
url = new URL(FMCurl);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setUseCaches(false);
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestMethod("POST");
conn.setRequestProperty("Authorization","key=" + authKey);
conn.setRequestProperty("Content-Type","application/json");
JSONObject json = new JSONObject();
json.put("to",userDeviceIdKey);
json.put("priority","high");
JSONObject info = new JSONObject();
info.put("title", title); // 通知标题
info.put("body", body); // 通知内容
info.put("var1", chatID);
info.put("var2",receiverID);
info.put("var3",itemID);
json.put("data", info);
OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
wr.write(json.toString());
wr.flush();
Log.w("", "getInstanceId failed" + json);
conn.getInputStream();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
e.printStackTrace();
}
return null;
}
}
而在我的服务中,我创建了:
public class MyFirebaseMessagingService extends FirebaseMessagingService {
@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
Log.d("TESTING_MESSAGE", "" + remoteMessage);
}
}
然而,当我发送消息时,似乎从未收到这个Log
,并且onMessageReceived
似乎从未被调用。
有什么原因吗?
我的下一个目标是在onMessageReceived
内创建通知,但我首先想确保我已经到达那里。
我的清单文件如下:
<service
android:name=".service.MyFirebaseMessagingService"
android:permission="com.google.android.c2dm.permission.SEND">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT" />
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
</intent-filter>
</service>
英文:
I have created an app where I have chat in it.
I would like that the users will receive a notification that they got a new message whenever they are outside of the app.
In order to do so, I'm using Firebase
service.
Now, whenever a message is sent, I call this method:
I have created the following MyFirebaseMessagingService
class to test when it is called:
private class MyTask extends AsyncTask<MyTaskParams, Void, Void> {
@Override
protected Void doInBackground(MyTaskParams... params) {
String userDeviceIdKey = params[0].url;
String title = params[0].title;
String body = params[0].body;
String authKey = "XXXXX"; // You FCM AUTH key
String FMCurl = "https://fcm.googleapis.com/fcm/send";
URL url;
try {
url = new URL(FMCurl);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setUseCaches(false);
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestMethod("POST");
conn.setRequestProperty("Authorization","key="+authKey);
conn.setRequestProperty("Content-Type","application/json");
JSONObject json = new JSONObject();
json.put("to",userDeviceIdKey);
json.put("priority","high");
JSONObject info = new JSONObject();
info.put("title", title); // Notification title
info.put("body", body); // Notification body
info.put("var1", chatID);
info.put("var2",receiverID);
info.put("var3",itemID);
json.put("data", info);
OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
wr.write(json.toString());
wr.flush();
Log.w("", "getInstanceId failed" + json);
conn.getInputStream();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
e.printStackTrace();
}
return null;
}
}
and In my Service I created:
public class MyFirebaseMessagingService extends FirebaseMessagingService {
@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
Log.d("TESTING_MESSAGE", "" + remoteMessage);
}
}
However, It seems like I never get this Log
when I send a message and it doesnt look like onMessageReceived
is ever called.
Is there any reason?
My next goal is to make notification inside onMessageReceived
but I want to make sure first that I get there.
My manifest is:
<service
android:name=".service.MyFirebaseMessagingService"
android:permission="com.google.android.c2dm.permission.SEND">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT" />
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
</intent-filter>
</service>
答案1
得分: 1
我使用你的代码制作了一个演示应用,它能够很好地工作,当消息到达时我可以看到onMessageReceived函数被触发。
我使用的是firebase-messaging版本20.1.7
implementation 'com.google.firebase:firebase-messaging:20.1.7'
因此我认为你应该进行以下检查:
-
检查你的应用是否在前台运行。因为当应用在后台时无法触发onMessageReceived。参考:https://firebase.google.com/docs/cloud-messaging/android/receive#handling_messages
-
检查当你发送HTTP请求时,是否写了正确的设备令牌(你的字段'userDeviceIdKey')。
-
检查你的HTTP请求在catch块中是否有错误。
希望能对你有所帮助。
英文:
I make a demo app with your code, and it works well and I can see that onMessageReceived function is trigged when a message arrives.
I use the firebase-messaging version 20.1.7
implementation 'com.google.firebase:firebase-messaging:20.1.7'
so I think you should do the following checking:
-
check if your app is in the foreground. because you can't trigger onMessageReceived when the app is in the background. refer: https://firebase.google.com/docs/cloud-messaging/android/receive#handling_messages
-
check if you wrote the right device token(your field 'userDeviceIdKey') when you sent the http request.
-
check if your http request has some error in catch.
hope can help you.
答案2
得分: 0
onMessageReceived()
方法在应用程序被杀死时不会被调用。
https://stackoverflow.com/questions/37358462/firebase-onmessagereceived-not-called-when-app-in-background
英文:
The onMessageReceived()
method will never be called if the app is killed.
https://stackoverflow.com/questions/37358462/firebase-onmessagereceived-not-called-when-app-in-background
答案3
得分: 0
首先,检查您发送的内容:数据消息还是通知消息。
它们可能看起来相同,但根据消息类型,调用不同的方法。
请查看此链接:https://firebase.google.com/support/faq/#fcm-android-background
// 检查消息是否包含通知载荷。
if (remoteMessage.getNotification() != null) {
Map test = remoteMessage.getData();
Log.d(TAG, "Message data payload: " + test);
// 检查消息是否包含数据载荷。
if (remoteMessage.getData().size() > 0) {
if (remoteMessage.getNotification() != null) {
Log.d(TAG, "Message Notification Body: " +
remoteMessage.getNotification().getBody());
英文:
First of all check what you send: data message or notification message.
They may look the same, but depending on what type of message, the different method called.
Check this out: https://firebase.google.com/support/faq/#fcm-android-background
// Check if message contains a notification payload.
if (remoteMessage.getNotification() != null) {
Map test = remoteMessage.getData();
Log.d(TAG, "Message data payload: " + test);
// Check if message contains a data payload.
if (remoteMessage.getData().size() > 0) {
if (remoteMessage.getNotification() != null) {
Log.d(TAG, "Message Notification Body: " +
remoteMessage.getNotification().getBody());
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论