i'm using FCM and follow instructions on firebase site but notifications not working when app in background
i already sync gradle library and download json file and sync done but not notifications recieved when app in background
app gradle
dependencies {
///////
}
apply plugin: 'com.google.gms.google-services'
dependencies {
classpath 'com.android.tools.build:gradle:3.5.1'
classpath 'com.google.gms:google-services:4.3.2'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
You have to add
classpath 'com.android.tools.build:gradle:3.5.1'
classpath'com.google.gms:google-services:4.3.2'
in project gradle and google plugin in app gradle file.
Then add the following dependencies:
implementation 'com.google.firebase:firebase-core:17.2.0'
implementation 'com.google.firebase:firebase-messaging:19.0.0'
You need to create a service of FCM to recieve notifications.
public class MyFirebaseMessagingService extends FirebaseMessagingService {
private NotificationManager notificationManager;
private static final String ADMIN_CHANNEL_ID = "CHANNEL_ID";
#Override
public void onNewToken(String s) {
super.onNewToken( s );
}
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
super.onMessageReceived( remoteMessage );
Map<String, String> data = remoteMessage.getData();
String body = data.get("body");
String title = data.get("title");
String image = data.get("image");
notificationManager = (NotificationManager) getSystemService( Context.NOTIFICATION_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
setupChannels( title, body );
}
Log.d( "Notification", "onMessageReceived: " + image);
Intent notificationIntent = new Intent(this, NotificationActivity.class);
notificationIntent.setFlags( Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_SINGLE_TOP );
PendingIntent pendingIntent = PendingIntent.getService( this, 0, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT );
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder( this, ADMIN_CHANNEL_ID )
.setSmallIcon( R.drawable.ic_launcher_background )
.setContentTitle( remoteMessage.getNotification( ).getTitle( ) )
.setContentText( remoteMessage.getNotification( ).getBody( ) )
.setContentIntent( pendingIntent );
NotificationManager notificationManager = (NotificationManager) getSystemService( Context.NOTIFICATION_SERVICE );
notificationManager.notify( 0, notificationBuilder.build( ) );
}
#RequiresApi(api = Build.VERSION_CODES.O)
private void setupChannels(String adminChannelName, String adminChannelDescription) {
NotificationChannel adminChannel;
adminChannel = new NotificationChannel( ADMIN_CHANNEL_ID, adminChannelName, NotificationManager.IMPORTANCE_LOW );
adminChannel.setDescription( adminChannelDescription );
adminChannel.enableLights( true );
adminChannel.setLightColor( Color.RED );
adminChannel.enableVibration( true );
if (notificationManager != null) {
notificationManager.createNotificationChannel( adminChannel );
}
}
}
And add this code to your manifest:
<service
android:name=".MyFirebaseMessagingService"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT" />
</intent-filter>
</service>
There are several steps for achieving the notification when application is in background.
You need to use POST parameter in Android FCM service.
You need to code down the thing inside onMessageReceived() from FCM dependencies.
https://firebase.google.com/docs/cloud-messaging/android/receive#handling_messages
because i just send notification without message body
i tried solution i just found that i forget this gradle library
implementation 'com.google.firebase:firebase-messaging:20.0.0'
Related
Since I got to have push notifications working as required when app was in both background and foreground, I have executed 30-40 notifications while testing (in 2 days), all of them sounding properly when arrived to android device (my custom notification channel also appeared in device settings as expected).
Suddenly, notifications continue arriving but without the sound (and custom notification channel does not appear in settings as before did). Since this, it is impossible for me to have sound back on notifications (neither background nor foreground).
Have not changed any involved code. I think sound has stopped because the notification channel is not being created for some reason. Have anyone experienced this or can help me?
Key code for case 'App in background':
1. Manifest.
<meta-data
android:name="com.google.firebase.messaging.default_notification_channel_id"
android:value="my_fcm_default_channel" />
2. Launching activity - onCreate():
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
// Create channel to show notifications.
val channelName = "Custom notification channel"
val defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION)
val notificationManager = getSystemService(NotificationManager::class.java)
val channel = NotificationChannel("my_fcm_default_channel",
channelName,
NotificationManager.IMPORTANCE_HIGH)
channel.setSound(defaultSoundUri, AudioAttributes.Builder().build()) // Not working
channel.enableLights(true)
channel.lightColor = Color.WHITE
channel.enableVibration(true)
channel.vibrationPattern = longArrayOf(100, 200, 100, 200, 100, 200, 100)
notificationManager.createNotificationChannel(channel)
}
3. Cloud function node.js snippet code:
// Notification details.
const payload = {
notification: {
title: 'Some title',
body: 'Some message',
sound: 'default',
click_action: "OPEN_ACTIVITY_3"
},
data: {
name: 'notification_3'
}
};
UPDATE:
Key code for case 'App in foreground':
1. MyFirebaseMessagingService - onMessageReceived():
val name = remoteMessage.data["name"] ?: ""
var intent: Intent? = null
when (name) {
"notification_1" -> {
intent = Intent(this, Activity1::class.java)
}
"notification_2" -> {
intent = Intent(this, Activity2::class.java)
}
"notification_3" -> {
val clickAction = remoteMessage.notification?.clickAction
clickAction?.let {
intent = Intent(clickAction)
intent?.putExtra("name", name)
}
}
"notification_4" -> {
intent = Intent(this, Activity4::class.java)
}
}
intent?.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
val pendingIntent = PendingIntent.getActivity(this, 0 /* Request code */, intent,
PendingIntent.FLAG_ONE_SHOT)
val defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION)
val notificationBuilder = NotificationCompat.Builder(this, "my_fcm_default_channel")
.setSmallIcon(R.drawable.common_google_signin_btn_icon_dark) // Dummy icon
.setContentTitle(remoteMessage.notification?.title ?: "")
.setContentText(remoteMessage.notification?.body ?: "")
.setAutoCancel(true)
.setSound(defaultSoundUri)
.setVibrate(longArrayOf(100, 200, 100, 200, 100, 200, 100))
.setContentIntent(pendingIntent)
.setDefaults(Notification.DEFAULT_ALL) // this line sets the default vibration and sound for notification
val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
// Since android Oreo notification channel is needed.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
val channel = NotificationChannel("my_fcm_default_channel",
"Custom notification channel",
NotificationManager.IMPORTANCE_HIGH)
channel.setSound(defaultSoundUri, AudioAttributes.Builder().build()) // Not working
channel.enableLights(true)
channel.lightColor = Color.WHITE
channel.enableVibration(true)
channel.vibrationPattern = longArrayOf(100, 200, 100, 200, 100, 200, 100)
notificationManager.createNotificationChannel(channel)
}
notificationManager.notify(0 /* ID of notification */, notificationBuilder.build())
i'm new to firebase cloud function and fcm, My situation is Whenever a new article is published in the database, I need to show the notification to my app user.
firebase cloud function worked perfectly but notification not received by device android.
cloud function
var functions = require('firebase-functions');
var admin = require('firebase-admin');
admin.initializeApp(functions.config().firebase);
exports.sendNotification = functions.database.ref('/Vacancy/{articleId}')
.onWrite((event: { after: any; }) => {
console.log("Successfully sent message:2");
var eventSnapshot = event.after;
var str1 = "Author is ";
var str = str1.concat(eventSnapshot.child("author").val());
console.log(str);
var topic = "android";
var payload = {
data: {
title: eventSnapshot.child("title").val(),
author: eventSnapshot.child("author").val()
}
};
return admin.messaging().sendToTopic(topic, payload)
.then(function (response: any) {
console.log("Successfully sent message:", response);
})
.catch(function (error: any) {
console.log("Error sending message:", error);
});
});
manifess code
<service
android:name=".ServiceNotification.NotificationMessagingService">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT"/>
</intent-filter>
</service>
NotificationMessagingService class code
public class NotificationMessagingService extends FirebaseMessagingService {
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
FirebaseMessaging.getInstance().subscribeToTopic("android");
if (remoteMessage.getData().size() > 0) {
showNotification(remoteMessage.getData().get("title"), remoteMessage.getData().get("author"));
}
if (remoteMessage.getNotification() != null) {
}
}
private void showNotification(String title, String author) {
Intent intent = new Intent(this, HomeActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0 /* Request code */, intent,
PendingIntent.FLAG_ONE_SHOT);
Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setContentTitle("New Article: " + title)
.setSmallIcon(R.mipmap.ic_launcher)
.setContentText("By " + author)
.setAutoCancel(true)
.setSound(defaultSoundUri)
.setContentIntent(pendingIntent);
NotificationManager notificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.notify(0 /* ID of notification */, notificationBuilder.build());
}
}
cloud function log
1:33:46.257 AM
sendNotification
Successfully sent message:2
1:33:46.263 AM
sendNotification
Author is Raja
1:33:47.022 AM
sendNotification
Successfully sent message: { messageId: 5711725841493019000 }
1:33:47.040 AM
sendNotification
Function execution took 1005 ms, finished with status: 'ok'
I have implemented firebase cloud messaging in my Android app. When I send notification from backed or Firebase console onMessageReceived() is triggered twice and generates two notifications on device. I've tried to search on internet but no results found for this problem
here is my code,
MyFirebaseNotificationService.java
public class MyFirebaseNotificationService extends FirebaseMessagingService {
#Override
public void onNewToken(String s) {
super.onNewToken(s);
MyApp.getInstance().saveFCMToken(s);
}
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
int notificationId = new Random().nextInt(60000);
String customerId = "";
Log.e("NOTIF", "" + remoteMessage.getData());
Intent notificationIntent = new Intent(this, SplashActivity.class);
notificationIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_CLEAR_TASK);
notificationIntent.setAction(Long.toString(System.currentTimeMillis()));
final PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, PendingIntent.FLAG_ONE_SHOT);
Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, "100")
.setSmallIcon(R.drawable.ic_app_icon)
.setColorized(true)
.setPriority(PRIORITY_HIGH)
.setColor(ContextCompat.getColor(getApplicationContext(), R.color.colorPrimary))
.setContentTitle(Html.fromHtml(remoteMessage.getData().get("title")))
.setContentText(Html.fromHtml(remoteMessage.getData().get("message")))
.setAutoCancel(true)
.setDefaults(Notification.DEFAULT_SOUND)
.setSound(defaultSoundUri)
.setContentIntent(pendingIntent);
createNotificationChannel();
NotificationManagerCompat notificationManager = NotificationManagerCompat.from(this);
notificationManager.notify(notificationId, notificationBuilder.build());
}
private void createNotificationChannel() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
CharSequence name = "Exchange Customer";
String description = "Sales Buddy";
String CHANNEL_ID = "100";
int importance = NotificationManager.IMPORTANCE_DEFAULT;
NotificationChannel channel = new NotificationChannel(CHANNEL_ID, name, importance);
channel.setDescription(description);
getSystemService(NotificationManager.class).createNotificationChannel(channel);
}
}
}
AndroidManifest
<service android:name=".sevices.MyFirebaseNotificationService"
android:exported="false">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT" />
</intent-filter>
</service>
Permissions in Manifest
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<uses-permission android:name="android.permission.READ_PROFILE" />
<uses-permission android:name="android.permission.READ_CONTACTS" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
<uses-feature
android:name="android.hardware.camera"
android:required="true" />
On Message received I've logged notification and here is logcat
2019-05-01 15:08:54.415 29417-29501/in.example.one E/NOTIF: {extras={"customerId":"5e341186-6bd4-11e9-9069-44a8422a303b"}, type=exchange, title=Test User:1556703533, message=Test User1}
2019-05-01 15:08:58.542 29417-29501/in.example.one E/NOTIF: {extras={"customerId":"5e341186-6bd4-11e9-9069-44a8422a303b"}, type=exchange, title=Test User:1556703533, message=Test User1}
here you can see same notification log is printing twice and both notifications are displaying on device
Project Gradle File
dependencies {
classpath 'com.android.tools.build:gradle:3.4.0'
classpath 'com.google.gms:google-services:4.2.0'
classpath 'io.fabric.tools:gradle:1.26.1'
}
Module Gradle File
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.android.support:design:28.0.0'
implementation 'com.android.support.constraint:constraint-layout:1.1.3'
testImplementation 'junit:junit:4.12'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
implementation 'com.android.support:recyclerview-v7:28.0.0'
implementation 'com.android.support:cardview-v7:28.0.0'
implementation 'com.squareup.picasso:picasso:2.5.2'
implementation 'com.amitshekhar.android:android-networking:1.0.2'
implementation 'com.github.WindSekirun:SectionCalendarView:1.0.5.1'
implementation 'com.github.darsh2:MultipleImageSelect:v0.0.4'
implementation 'com.bogdwellers:pinchtozoom:0.1'
implementation 'com.google.firebase:firebase-core:16.0.8'
implementation 'com.google.firebase:firebase-messaging:17.6.0'
implementation 'com.crashlytics.sdk.android:crashlytics:2.9.9'
implementation 'com.google.firebase:firebase-database:16.1.0'
}
My Php code
$extras= json_encode(['customerId' => "5e341186-6bd4-11e9-9069-44a8422a303b"]);
$data=array(
'title'=> "Test User:".time(),
'message'=> "Test User1",
'type'=> "exchange",
'extras'=>$extras
);
$notification=array(
'title'=> "Test User:".time(),
'body'=> "body1",
);
$fields = array
(
'to'=>'/topics/test-exchange-persons-sales-buddy',
'data' => $data
);
$headers = array
(
'Authorization: key=' . API_ACCESS_KEY,
'Content-Type: application/json'
);
$ch = curl_init();
curl_setopt( $ch,CURLOPT_URL, 'https://fcm.googleapis.com/fcm/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 );
curl_close( $ch );
echo $result;
I have the same issue since yesterday (using topics too). As a workaround, until it gets fixed I'm doing this in my FirebaseMessagingService:
private static ArrayList<Long> alreadyNotifiedTimestamps = new ArrayList<>();
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
if (!isDuplicate(remoteMessage.getSentTime())) {
// send notificaiton here
}
}
// Workaround for Firebase duplicate pushes
private boolean isDuplicate(long timestamp) {
if (alreadyNotifiedTimestamps.contains(timestamp)) {
alreadyNotifiedTimestamps.remove(timestamp);
return true;
} else {
alreadyNotifiedTimestamps.add(timestamp);
}
return false;
}
I have tha same problem but with Firebase Messaging Topics. I recive two notification beacuase "onMessageReceived" called twice like you. Maybe a problem from FCM today?
I had also faced similar issue, Because of implementation 'com.google.firebase:firebase-messaging:17.6.0', So then i just used implementation 'com.google.firebase:firebase-messaging:17.3.3' version of messaging then everything worked correctly
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID);
was showing the error:
Builder (Context) in Builder cannot be applied to (FirebaseMessagingService, java.lang.String)
Help me to solve this problem.
I tried Notification.Builder notificationBuilder = new Notification.Builder(this, NOTIFICATION_CHANNEL_ID);
and
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this);
But it was not working in both API 23 and API 27.
Here is the code
import android.app.Notification;
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.Intent;
import android.graphics.Color;
import android.os.Build;
import android.support.annotation.RequiresApi;
import android.support.v7.app.NotificationCompat;
import com.google.firebase.messaging.RemoteMessage;
public class FirebaseMessagingService extends com.google.firebase.messaging.FirebaseMessagingService {
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
super.onMessageReceived(remoteMessage);
String notification_title = remoteMessage.getData().get("title");
String notification_msg = remoteMessage.getData().get("body");
String from_user_id = remoteMessage.getData().get("from_user_id");
String click_action = remoteMessage.getData().get("click_action");
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
String NOTIFICATION_CHANNEL_ID = "channel_id_01";
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, "My Notifications", NotificationManager.IMPORTANCE_HIGH);
// Configure the notification channel.
notificationChannel.setDescription("Channel description");
notificationChannel.enableLights(true);
notificationChannel.setLightColor(Color.BLUE);
notificationChannel.setVibrationPattern(new long[]{0, 1000, 500, 1000});
notificationChannel.enableVibration(true);
notificationManager.createNotificationChannel(notificationChannel);
}
Intent intent = new Intent(click_action);
intent.putExtra("user_id", from_user_id);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID);
notificationBuilder.setAutoCancel(true).setDefaults(Notification.DEFAULT_ALL).setWhen(System.currentTimeMillis()).setSmallIcon(R.drawable.logo1).setPriority(Notification.PRIORITY_MAX).setContentTitle(notification_title).setContentText(notification_msg).setContentInfo("Info").setContentIntent(pendingIntent);
int mNotificationId = (int) System.currentTimeMillis();
notificationManager.notify(mNotificationId, notificationBuilder.build());
}
}
build.gradle
apply plugin: 'com.android.application'
android {
compileSdkVersion 28
defaultConfig {
applicationId "com.example.android.gabwithus"
minSdkVersion 16
targetSdkVersion 28
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'com.android.support:appcompat-v7:28.0.0-alpha3'
implementation 'com.android.support:design:28.0.0-alpha3'
implementation 'com.android.support.constraint:constraint-layout:1.1.2'
implementation 'com.google.firebase:firebase-auth:16.0.2'
implementation 'com.google.firebase:firebase-core:16.0.1'
implementation 'com.google.firebase:firebase-database:16.0.1'
implementation 'com.google.firebase:firebase-messaging:17.1.0'
implementation 'com.android.support:support-v4:28.0.0-alpha3'
implementation 'com.google.firebase:firebase-storage:15.0.0'
implementation 'com.theartofdev.edmodo:android-image-cropper:2.7.0'
testImplementation 'junit:junit:4.12'
implementation 'com.squareup.picasso:picasso:2.5.2'
implementation 'com.firebaseui:firebase-ui-database:2.0.1'
implementation 'com.squareup.okhttp:okhttp:2.5.0'
implementation 'id.zelory:compressor:2.1.0'
implementation 'com.android.support:support-media-compat:28.0.0-alpha3'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
implementation 'de.hdodenhof:circleimageview:2.2.0'
implementation 'com.theartofdev.edmodo:android-image-cropper:2.5.1'
implementation 'com.facebook.fresco:fresco:1.5.0'
}
apply plugin: 'com.google.gms.google-services'
configurations.all {
resolutionStrategy.eachDependency { DependencyResolveDetails details ->
def requested = details.requested
if (requested.group == 'com.android.support') {
if (!requested.name.startsWith("multidex")) {
details.useVersion '25.3.0'
}
}
}
}
Try to use this, I think your problem is here: details.useVersion '25.3.0'
configurations.all {
resolutionStrategy.eachDependency { DependencyResolveDetails details ->
def requested = details.requested
if (requested.group == 'com.android.support') {
if (!requested.name.startsWith("multidex")) {
details.useVersion '27.1.0'
}
}
}
}
The problem is that you're using import android.support.v7.app.NotificationCompat. The v7.app.NotificationCompat was actually removed in revision 27.0.0 and was never updated to support Notification Channels.
You should remove that line and instead import android.support.v4.app.NotificationCompat, which does support Notification Channels.
its work in all api Try this :
public void sendNotification(String messageBody) {
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
NotificationCompat.Builder builder =
new NotificationCompat.Builder(this)
.setSmallIcon(R.drawable.ic_enable_notification_icon)
.setColor(Color.parseColor("#5878f2"))
.setContentTitle(getString(R.string.app_name))
.setContentText(messageBody)
.setAutoCancel(true);
Intent notificationIntent = new Intent(this, MainActivity.class);
notificationIntent.putExtra("message",messageBody);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent,
PendingIntent.FLAG_UPDATE_CURRENT);
builder.setContentIntent(contentIntent);
if(Build.VERSION_CODES.O <= Build.VERSION.SDK_INT) {
builder.setChannelId(createNotificationChannel());
}
Notification notification = builder.build();
notificationManager.notify(211, notification);
}
#RequiresApi(api = Build.VERSION_CODES.O)
private String createNotificationChannel(){
String channelId = "demo";
String channelName = "My demo";
NotificationChannel mChannel = new NotificationChannel(channelId,channelName, NotificationManager.IMPORTANCE_NONE);
mChannel.setImportance(NotificationManager.IMPORTANCE_HIGH);
NotificationManager mNotificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
if (mNotificationManager != null) {
mNotificationManager.createNotificationChannel(mChannel);
}
return channelId;
}
Android version O and above need notification channel. here is one working example for you.getRequestCode method is for different notification so that they will not replace. you can use any number also. If you use same number notification will replace automatically, so I use a random number generator.
private static int getRequestCode() {
Random rnd = new Random();
return 100 + rnd.nextInt(900000);
}
PendingIntent pendingIntent = PendingIntent.getActivity(this, getRequestCode() /* Request code */, intent,
PendingIntent.FLAG_ONE_SHOT);
Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setSmallIcon(R.mipmap.ic_launcher)
.setLargeIcon(BitmapFactory.decodeResource(this.getResources(),
R.mipmap.ic_launcher))
.setContentTitle(neplaiTile) // use your own title
.setContentText(message) // use your own message
.setAutoCancel(true)
.setSound(defaultSoundUri)
.setContentIntent(pendingIntent)
.setPriority(Notification.PRIORITY_MAX)
.setBadgeIconType(Notification.BADGE_ICON_SMALL);
NotificationManager notificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
int importance = NotificationManager.IMPORTANCE_HIGH;
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, "NOTIFICATION_CHANNEL_NAME", importance);
notificationChannel.enableLights(true);
notificationChannel.setLightColor(Color.RED);
notificationChannel.enableVibration(true);
notificationChannel.setVibrationPattern(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400});
assert notificationManager != null;
notificationBuilder.setChannelId(NOTIFICATION_CHANNEL_ID);
notificationManager.createNotificationChannel(notificationChannel);
}
assert notificationManager != null;
notificationManager.notify(getRequestCode() /* Request Code */, notificationBuilder.build());
I'm trying to use FCM to send notifications. I'm building an app using Xamarin, so I followed this tutorial to set up my notifications.
Here my firebase service:
[Service]
[IntentFilter(new[] { "com.google.firebase.INSTANCE_ID_EVENT" })]
public class MyFirebaseIIDService : FirebaseInstanceIdService
{
const string TAG = "MyFirebaseIIDService";
public override void OnTokenRefresh()
{
var refreshedToken = FirebaseInstanceId.Instance.Token;
System.Diagnostics.Debug.WriteLine(TAG, "Refreshed token: " + refreshedToken);
SendRegistrationToServer(refreshedToken);
}
void SendRegistrationToServer(string token)
{
// Add custom implementation, as needed.
}
}
[Service]
[IntentFilter(new[] { "com.google.firebase.MESSAGING_EVENT" })]
public class MyFirebaseMessagingService : FirebaseMessagingService
{
const string TAG = "MyFirebaseMsgService";
public override void OnMessageReceived(RemoteMessage message)
{
Android.Util.Log.Debug(TAG, "From: " + message.From);
Android.Util.Log.Debug(TAG, "Notification Message Body: " + message.GetNotification().Body);
}
void SendNotification(string messageBody)
{
var intent = new Intent(this, typeof(MainActivity));
intent.AddFlags(ActivityFlags.ClearTop);
var pendingIntent = PendingIntent.GetActivity(this, 0 /* Request code */, intent, PendingIntentFlags.OneShot);
var defaultSoundUri = RingtoneManager.GetDefaultUri(RingtoneType.Notification);
var notificationBuilder = new NotificationCompat.Builder(this)
.SetContentTitle("FCM Message")
.SetContentText(messageBody)
.SetAutoCancel(true)
.SetSound(defaultSoundUri)
.SetContentIntent(pendingIntent);
var notificationManager = NotificationManager.FromContext(this);
notificationManager.Notify(0, notificationBuilder.Build());
}
}
I had an issue with the refresh token malfunctioning from time to time so I added this to my MainActivity:
if (IsPlayServicesAvailable())
{
var json = "";
using (StreamReader sr = new StreamReader(Assets.Open("google_services.json")))
{
json = sr.ReadToEnd();
}
var options_from_json = JObject.Parse(json);
try
{
var options = new FirebaseOptions.Builder()
.SetApplicationId(options_from_json["client"][0]["client_info"]["mobilesdk_app_id"].ToString())
.SetApiKey(options_from_json["client"][0]["api_key"][0]["current_key"].ToString())
//.SetDatabaseUrl("Firebase-Database-Url")
.SetGcmSenderId(options_from_json["project_info"]["project_number"].ToString())
.Build();
var firebaseApp = FirebaseApp.InitializeApp(this, options);
}
catch (IllegalStateException e)
{
System.Diagnostics.Debug.WriteLine("L'app firebase existe déjà, donc il n'y a rien à faire.");
}
await Task.Run(() =>
{
var instanceID = FirebaseInstanceId.Instance;
var iid1 = instanceID.Token;
var iid2 = instanceID.GetToken(options_from_json["project_info"]["project_number"].ToString(), Firebase.Messaging.FirebaseMessaging.InstanceIdScope);
System.Diagnostics.Debug.WriteLine("Iid1: {0}, iid2: {1}", iid1, iid2);
});
}
Fine, so far I've got token for emulators as well as real life devices.
My problem is the reception of notification: it's really hazardous, sometime I get some an instant after I hit send on FCM console, sometime I have to reboot the device, sometime it just takes hours to arrive and sometime I just receive nothing... My setup doesn't change and the devices aren't on a wifi.
Any clues?