I am trying to catch key-value data from firebase messaging, i.e. by receiving notifications from firebase. I made a class for functionality and then assigned values to two global variables. Still, when I receive notification and click on it, no data is shown in my ui. Even title and body of notification is not shown when I start my app from scratch, i.e. first I run my app, close it, receive notification and then open it by clicking on it. I want that whether my app is closed, running in background or opened, key-value data could be feteched and desplayed on UI.
Here is my code -
variables.dart -
import 'package:flutter/cupertino.dart';
ValueNotifier<String> data = ValueNotifier("");
ValueNotifier<String> bodyData = ValueNotifier("");
notification.dart -
import 'dart:async';
import 'package:firebase_core/firebase_core.dart';
import 'package:firebase_messaging/firebase_messaging.dart';
import 'package:flutter/material.dart';
import 'package:flutter_application_notifications/variables.dart';
Future<void> onBackgroundMessage(RemoteMessage message) async {
await Firebase.initializeApp();
if (message.data.containsKey("data")) {
data.value = message.data["data"];
}
if (message.data.containsKey("body")) {
bodyData.value = message.data['body'];
}
}
class Messaging {
final firebaseMessaging = FirebaseMessaging.instance;
final streamController = StreamController<String>.broadcast();
final titleController = StreamController<String>.broadcast();
final bodyController = StreamController<String>.broadcast();
setNotifications() {
FirebaseMessaging.onBackgroundMessage(onBackgroundMessage);
FirebaseMessaging.onMessage.listen((message) async {
if (message.data.containsKey('data')) {
streamController.sink.add(message.data['data']);
}
if (message.data.containsKey('notification')) {
streamController.sink.add(message.data['notification']);
}
titleController.sink
.add(message.notification?.title ?? "Recieved Null Title");
bodyController.sink
.add(message.notification?.body ?? "Recieved Null Body");
});
final token = firebaseMessaging
.getToken()
.then((value) => print("Token is - $value"));
}
dispose() {
streamController.close();
bodyController.close();
titleController.close();
}
}
main.dart -
import 'package:firebase_core/firebase_core.dart';
import 'package:flutter/material.dart';
import 'package:flutter_application_notifications/notification.dart';
import 'package:flutter_application_notifications/variables.dart';
void main() async {
await init();
runApp(const MyApp());
}
Future init() async {
WidgetsFlutterBinding.ensureInitialized();
await Firebase.initializeApp();
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: const MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({Key? key, required this.title}) : super(key: key);
final String title;
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
String notificationTitle = "No title";
String notificationBody = "No Body";
String notificationData = "No Data";
int _counter = 0;
@override
void initState() {
super.initState();
final firebaseMessaging = Messaging();
firebaseMessaging.setNotifications();
firebaseMessaging.streamController.stream.listen(_changeData);
firebaseMessaging.bodyController.stream.listen(_changeBody);
firebaseMessaging.titleController.stream.listen(_changeTitle);
}
_changeData(String message) {
setState(() {
notificationData = message;
});
}
_changeTitle(String message) {
setState(() {
notificationTitle = message;
});
}
_changeBody(String message) {
setState(() {
notificationBody = message;
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
"Title is - $notificationTitle",
),
Text(
"Body is - $notificationBody",
),
Text(
"Data is - $notificationData",
),
ValueListenableBuilder(
valueListenable: data,
builder: (context, value, child) {
return Text('Received data is $value');
},
),
],
),
),
);
}
}
