FCM通知在App后台/关闭时无法打开指定页面求助
FCM通知跳转异常问题
需求:用户点击通知时,在WebView中打开指定链接。
正常场景:App处于前台时,用户点击通知可正常跳转到目标URL。
异常场景:App未启动或处于后台时,点击通知仅打开App,无法跳转到指定URL。
已查阅相关资料但未找到解决方案。
FirebaseMessagingService代码
public class FcmMessagingService extends FirebaseMessagingService { @Override public void onMessageReceived(RemoteMessage remoteMessage) { // Also if you intend on generating your own notifications as a result of a received FCM // message, here is where that should be initiated. See sendNotification method below. String title = remoteMessage.getNotification().getTitle(); final String message = remoteMessage.getNotification().getBody(); String click_action = remoteMessage.getData().get("click_action"); sendOnChannel1(title, message, click_action); } private void sendOnChannel1(String title, String messageBody, String click_action) { Intent activityIntent = new Intent(this, MainActivity.class); activityIntent.putExtra("linkz", click_action); PendingIntent contentIntent = PendingIntent.getActivity(this, 1 /* Request code */, activityIntent, 0); String channelId = "fcm_default_channel"; Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION); NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, channelId) .setSmallIcon(R.mipmap.ic_icon) .setContentTitle(title) .setContentText(messageBody) .setPriority(NotificationCompat.PRIORITY_HIGH) .setCategory(NotificationCompat.CATEGORY_REMINDER) //.setColor(Color.BLUE) .setSound(defaultSoundUri) .setContentIntent(contentIntent) .setAutoCancel(true) .setOnlyAlertOnce(true); //.addAction(R.mipmap.ic_launcher, "Toast", actionIntent); NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); // Since android Oreo notification channel is needed. if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { NotificationChannel channel = new NotificationChannel(channelId, "Channel human readable title", NotificationManager.IMPORTANCE_DEFAULT); notificationManager.createNotificationChannel(channel); } notificationManager.notify(1 /* ID of notification */, notificationBuilder.build()); } }
Manifest配置
<uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /> <uses-permission android:name="android.permission.CAMERA"/> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> <meta-data android:name="android.webkit.WebView.EnableSafeBrowsing" android:value="true" /> <application android:allowBackup="true" android:icon="@mipmap/ic_icon" android:label="@string/app_name" android:roundIcon="@mipmap/ic_icon" android:supportsRtl="true" android:theme="@style/AppTheme" android:hardwareAccelerated="true" android:usesCleartextTraffic="true"> <activity android:name=".MainActivity" android:parentActivityName=".welcome" android:screenOrientation="portrait" android:configChanges="orientation|screenSize" android:exported="true"> <intent-filter> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <activity android:name=".welcome" android:screenOrientation="portrait" android:configChanges="orientation|screenSize" android:exported="true"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> <intent-filter> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="http" android:host="www.careturtle.com" /> </intent-filter> </activity> <service android:name=".FcmMessagingService" android:exported="false" android:directBootAware="true"> <intent-filter> <action android:name="com.google.firebase.MESSAGING_EVENT" /> <category android:name="android.intent.category.DEFAULT" /> </intent-filter> </service> <meta-data android:name="com.google.firebase.messaging.default_notification_icon" android:resource="@mipmap/ic_icon" /> <activity android:name=".noconnection" android:screenOrientation="portrait"> </activity> </application>
解决方案
1. 修正PendingIntent标记
App在后台或未启动时,PendingIntent需要确保额外数据能正确传递,修改sendOnChannel1方法中的PendingIntent创建逻辑:
// 根据Android版本选择兼容标记 int flags; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { flags = PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE; } else { flags = PendingIntent.FLAG_UPDATE_CURRENT; } PendingIntent contentIntent = PendingIntent.getActivity(this, 1, activityIntent, flags);
2. 处理MainActivity的启动Intent
App未启动时,通知的跳转数据通过启动Intent传递,需要在MainActivity的两个生命周期方法中处理:
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); handleNotificationIntent(getIntent()); } @Override protected void onNewIntent(Intent intent) { super.onNewIntent(intent); handleNotificationIntent(intent); } private void handleNotificationIntent(Intent intent) { if (intent != null && intent.hasExtra("linkz")) { String targetUrl = intent.getStringExtra("linkz"); // 跳转到WebView页面加载目标链接 Intent webIntent = new Intent(this, WebViewActivity.class); webIntent.putExtra("url", targetUrl); startActivity(webIntent); } }
3. 清理Manifest的Launcher配置
当前两个Activity都设置了LAUNCHER类别,会导致启动入口混乱,保留一个Launcher Activity即可:
<activity android:name=".MainActivity" android:parentActivityName=".welcome" android:screenOrientation="portrait" android:configChanges="orientation|screenSize" android:exported="true"> <!-- 移除该Launcher intent-filter --> </activity>
4. 确保FCM消息数据格式正确
发送FCM消息时,click_action必须放在data字段中(而非notification字段),后端请求体示例:
{ "to": "设备令牌", "data": { "click_action": "目标URL", "title": "通知标题", "body": "通知内容" } }
5. 完善WebView页面加载逻辑
在WebView页面中确保能正确接收并加载传递的URL:
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_webview); WebView webView = findViewById(R.id.webView); if (getIntent() != null && getIntent().hasExtra("url")) { String url = getIntent().getStringExtra("url"); webView.loadUrl(url); } }
内容的提问来源于stack exchange,提问作者Observer
相关产品推荐
相关产品推荐

