I am developing an Android application that uses Firebase Cloud Messaging (FCM) to send notifications for incoming calls. I want to ensure that notifications are received even when the app is in the background. I have noticed that notifications only appear when the app is in the foreground. They do not show up when the app is running in the background< background img: enter image description here foreground img: enter image description here when android in backgorund . Logcat : win=Window{f06d548 u0 com.example.tr/com.example.tr.MainActivity} destroySurfaces: appStopped=true cleanupOnResume=false win.mWindowRemovalAllowed=false win.mRemoveOnExit=false win.mViewVisibility=8 caller=com.android.server.wm.ActivityRecord.destroySurfaces:6862 com.android.server.wm.ActivityRecord.destroySurfaces:6843 com.android.server.wm.ActivityRecord.activityStopped:7528 com.android.server.wm.ActivityClientController.activityStopped:310 android.app.IActivityClientController$Stub.onTransact:702 com.android.server.wm.ActivityClientController.onTransact:175 android.os.Binder.execTransactInternal:1380 AndroidManifest.xml <?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android"> <application android:allowBackup="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:roundIcon="@mipmap/ic_launcher_round" android:supportsRtl="true" android:theme="@style/AppTheme" android:usesCleartextTraffic="true"> <!-- Firebase Messaging Service --> <service android:name=".MyFirebaseMessagingService" android:exported="false"> <intent-filter> <action android:name="com.google.firebase.MESSAGING_EVENT" /> </intent-filter> </service> <meta-data android:name="com.google.firebase.messaging.default_notification_channel_id" android:value="incoming_calls" /> <activity android:name=".IncomingCallActivity"></activity> <!-- Main Activity --> <activity android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale|smallestScreenSize|screenLayout|uiMode" android:name=".MainActivity" android:label="@string/title_activity_main" android:theme="@style/AppTheme.NoActionBarLaunch" android:launchMode="singleTask" android:exported="true"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <!-- File Provider for handling file URIs --> <provider android:name="androidx.core.content.FileProvider" android:authorities="${applicationId}.fileprovider" android:exported="false" android:grantUriPermissions="true"> <meta-data android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/file_paths" /> <meta-data android:name="com.google.firebase.messaging.default_notification_icon" android:resource="@mipmap/ic_launcher_round" /> <meta-data android:name="com.google.firebase.messaging.default_notification_color" android:resource="@color/colorAccent" /> </provider> </application> <!-- Permissions --> <uses-permission android:name="android.permission.POST_NOTIFICATIONS" /> <uses-permission android:name="android.permission.FOREGROUND_SERVICE_PHONE_CALL" /> <uses-permission android:name="android.permission.DISABLE_KEYGUARD" /> <uses-permission android:name="android.permission.CALL_PHONE" /> <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" /> <uses-permission android:name="android.permission.VIBRATE" /> <!-- Incoming Call Permissions Start --> <uses-permission android:name="android.permission.WAKE_LOCK" /> <uses-permission android:name="android.permission.USE_FULL_SCREEN_INTENT" /> <uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" /> <uses-permission android:name="android.permission.FOREGROUND_SERVICE" /> <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" /> <permission android:name="android.permission.INTERACT_ACROSS_USERS_FULL" androidrotectionLevel="signature" /> <!-- Incoming Call Permissions End --> </manifest> MyFirebaseMessagingService.java package com.example.tr; import android.app.NotificationChannel; import android.app.NotificationManager; import android.app.PendingIntent; import android.content.Intent; import android.os.Build; import android.os.Handler; import android.os.Looper; import android.util.Log; import android.content.Context; import android.os.Vibrator; import androidx.core.app.NotificationCompat; import com.google.firebase.messaging.FirebaseMessagingService; import com.google.firebase.messaging.RemoteMessage; public class MyFirebaseMessagingService extends FirebaseMessagingService { private static final String TAG = "MyFirebaseMsgService"; private static final int NOTIFICATION_ID = 0; private static final int MISSED_CALL_NOTIFICATION_ID = 1; @Override public void onMessageReceived(RemoteMessage remoteMessage) { Log.d(TAG, "From: " + remoteMessage.getFrom()); if (remoteMessage.getData().size() > 0) { sendNotification(remoteMessage); } if (remoteMessage.getNotification() != null) { sendNotification(remoteMessage); } } private void sendNotification(RemoteMessage remoteMessage) { String title = "INCOMING CALL "; String body = remoteMessage.getData().get("callerName") + "Sizi arıyor "; //--> Intent intent = new Intent(this, IncomingCallActivity.class); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK); intent.putExtra("callerName", remoteMessage.getData().get("callerName")); intent.putExtra("callId", remoteMessage.getData().get("callId")); PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE); Intent acceptIntent = new Intent(this, IncomingCallActivity.class); acceptIntent.putExtra("callAction", "accept"); acceptIntent.putExtra("callerName", remoteMessage.getData().get("callerName")); acceptIntent.putExtra("callId", remoteMessage.getData().get("callId")); Intent declineIntent = new Intent(this, IncomingCallActivity.class); declineIntent.putExtra("callAction", "decline"); declineIntent.putExtra("callerName", remoteMessage.getData().get("callerName")); declineIntent.putExtra("callId", remoteMessage.getData().get("callId")); PendingIntent acceptPendingIntent = PendingIntent.getActivity(this, 1, acceptIntent, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE); PendingIntent declinePendingIntent = PendingIntent.getActivity(this, 2, declineIntent, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE); NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, "incoming_calls") .setContentTitle(title) .setContentText(body) .setSmallIcon(R.mipmap.ic_launcher) .setAutoCancel(true) .addAction(R.drawable.ic_accept, "Answer", acceptPendingIntent) .addAction(R.drawable.ic_decline, "Decline", declinePendingIntent) .setContentIntent(pendingIntent) .setPriority(NotificationCompat.PRIORITY_MAX) .setCategory(NotificationCompat.CATEGORY_CALL) .setVibrate(new long[]{0, 1000, 800}) .setVisibility(NotificationCompat.VISIBILITY_PUBLIC) .setFullScreenIntent(pendingIntent, true); NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { NotificationChannel channel = new NotificationChannel("incoming_calls", "Incoming Calls", NotificationManager.IMPORTANCE_HIGH); notificationManager.createNotificationChannel(channel); } notificationManager.notify(NOTIFICATION_ID, notificationBuilder.build()); Vibrator vibrator = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE); if (vibrator != null) { vibrator.vibrate(new long[]{0, 1000, 800}, 0); } new Handler(Looper.getMainLooper()).postDelayed(new Runnable() { @Override public void run() { notificationManager.cancel(NOTIFICATION_ID); sendMissedCallNotification(remoteMessage.getData().get("callerName")); if (vibrator != null) { vibrator.cancel(); } } }, 3000); } private void sendMissedCallNotification(String callerName) { String title = "Missed Call"; String body = "You missed a call from " + callerName; NotificationCompat.Builder missedCallBuilder = new NotificationCompat.Builder(this, "missed_calls") .setContentTitle(title) .setContentText(body) .setSmallIcon(R.mipmap.ic_launcher) .setAutoCancel(true) .setPriority(NotificationCompat.PRIORITY_HIGH); NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { NotificationChannel channel = new NotificationChannel("missed_calls", "Missed Calls", NotificationManager.IMPORTANCE_HIGH); notificationManager.createNotificationChannel(channel); } notificationManager.notify(MISSED_CALL_NOTIFICATION_ID, missedCallBuilder.build()); } } MainActivity.java package com.example.tr; import android.app.NotificationChannel; import android.app.NotificationManager; import android.os.Build; import android.os.Bundle; import com.getcapacitor.BridgeActivity; import com.google.firebase.FirebaseApp; public class MainActivity extends BridgeActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); FirebaseApp.initializeApp(this); createNotificationChannel(); } private void createNotificationChannel() { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { NotificationChannel channel = new NotificationChannel( "incoming_calls", // Channel ID "Incoming Calls", // Channel name NotificationManager.IMPORTANCE_HIGH ); channel.setDescription("Channel for incoming call notifications"); NotificationManager manager = getSystemService(NotificationManager.class); if (manager != null) { manager.createNotificationChannel(channel); } } } } IncomingCallActivity.java package com.example.tr; import android.widget.Button; import android.widget.TextView; import android.content.Intent; import android.os.Bundle; import androidx.annotation.Nullable; import androidx.appcompat.app.AppCompatActivity; import android.os.Vibrator; import android.util.Log; public class IncomingCallActivity extends AppCompatActivity { private Vibrator vibrator; @Override protected void onCreate( Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_incoming_call); Intent intent = getIntent(); String callerName = intent.getStringExtra("callerName"); String callId = intent.getStringExtra("callId"); String callAction = intent.getStringExtra("callAction"); TextView callerNameTextView = findViewById(R.id.caller_name); callerNameTextView.setText(callerName); vibrator = (Vibrator) getSystemService(VIBRATOR_SERVICE); Button acceptButton = findViewById(R.id.answer_button); acceptButton.setOnClickListener(v -> { Log.d("IncomingCallActivity", "Kabul butonuna tıklandı"); // finish(); if (vibrator != null) { vibrator.cancel(); } }); Button declineButton = findViewById(R.id.decline_button); declineButton.setOnClickListener(v -> { Log.d("IncomingCallActivity", "Reddet butonuna tıklandı"); // finish(); if (vibrator != null) { vibrator.cancel(); } }); } } api.service.ts: import { HttpClient, HttpHeaders } from '@angular/common/http'; import { Injectable } from '@angular/core'; import { Observable } from 'rxjs'; @Injectable({ providedIn: 'root' }) export class ApiService { static sendNotification(deviceToken: string) { throw new Error("Method not implemented."); } private apiUrl = ''; private accessToken ="" constructor(private http: HttpClient) {} sendNotification(token: string ): Observable<any> { const headers = new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': `Bearer ${this.accessToken}` }); console.log("send push noti token ->",token) const notificationData = { token: token, // notification: { // title: 'Incoming Calls', // body: 'aramanız varr', // }, data: { title: 'Incoming Call', body: 'Cevapsız aramanız var ', callType: 'incoming', callerName: 'John Doe', callId: '12345', priority: 'high' }, android: { priority: 'high', notification: { channel_id: 'incoming_calls', sound: 'default', // full_screen_intent: true, }, }, }; const body = { message: notificationData }; return this.http.post<any>(this.apiUrl, body, { headers }); } }``` `Home.page.ts` `` import { Component } from "@angular/core"; import { FirebaseMessaging, GetTokenOptions, } from "@capacitor-firebase/messaging"; import { Capacitor } from "@capacitor/core"; import { IonicModule } from "@ionic/angular"; import { environment } from "src/environments/environment"; import { NotificationService } from '../services/notification.service'; import { ApiService } from "../api/api.service"; @Component({ selector: "app-home", templateUrl: "home.page.html", styleUrls: ["home.page.scss"], standalone: true, imports: [IonicModule], }) export class HomePage { public token = ""; constructor( private notificationService: NotificationService, private apiService: ApiService ) { FirebaseMessaging.addListener("notificationReceived", (event) => { console.log("notificationReceived: ", { event }); }); FirebaseMessaging.addListener("notificationActionPerformed", (event) => { console.log("notificationActionPerformed: ", { event }); }); if (Capacitor.getPlatform() === "web") { navigator.serviceWorker.addEventListener("message", (event: any) => { console.log("serviceWorker message: ", { event }); const notification = new Notification(event.data.notification.title, { body: event.data.notification.body, }); notification.onclick = (event) => { console.log("notification clicked: ", { event }); }; }); } } public async requestPermissions(): Promise<void> { const result = await FirebaseMessaging.requestPermissions(); if (result.receive === 'granted') { console.log('Push notifications permission granted'); } } public async getToken(): Promise<void> { const options: GetTokenOptions = { vapidKey: environment.firebase.vapidKey, }; if (Capacitor.getPlatform() === "web") { options.serviceWorkerRegistration = await navigator.serviceWorker.register("firebase-messaging-sw.js"); } const { token } = await FirebaseMessaging.getToken(options); this.token = token; } sendPushNotification() { const deviceToken = "fIuEs9LlRwO6J06ahgWCtC:APA91bF5VnhsCYAyHxudm1de2s4sVYfUWkenKl8zvOxbjHa2_eOv5MlU2FNTogrPYu4bCJKKiNxM7LpQvc7w_iW59fKGoevE0OjYnYPrxHjj8x5T7uvqdW3_j3HXpTj3F_DrLYeBVpX4" console.log("Device token is here -> : ", deviceToken); if (!deviceToken) { console.error('No device token available. Unable to send notification.'); return; } this.apiService.sendNotification(deviceToken).subscribe( (response: any) => { console.log('Push notification sent:', response); }, (error: any) => { console.error('Error sending notification:', error); console.error('Full error response:', JSON.stringify(error.error)); } ); } } Continue reading...