flutter_awesome_notification 0.0.2 copy "flutter_awesome_notification: ^0.0.2" to clipboard
flutter_awesome_notification: ^0.0.2 copied to clipboard

A comprehensive notification plugin for Flutter with FCM, local notifications, and intelligent filtering.

Flutter Awesome Notification πŸ”” #

A comprehensive, production-ready notification plugin for Flutter apps with Firebase Cloud Messaging (FCM) and local notifications. Handles foreground, background and terminated notifications and navigation on notification tap.

✨ Features #

  • βœ… Foreground Notification Handling: Intelligent foreground notification management
  • βœ… Intelligent Filtering: Action step, chat room, and custom notification filtering
  • βœ… Navigation Integration: Custom callbacks for navigation handling
  • βœ… Topic Subscriptions: Easy FCM topic management
  • βœ… Local Notifications: Immediate and scheduled local notifications
  • βœ… Highly Configurable: Builder pattern with sensible defaults
  • βœ… Minimal Code: Easy setup with very little boilerplate
  • βœ… FCM Token Management: Automatic token handling and refresh
  • βœ… Custom Logging: Integrate with your preferred logging solution
  • βœ… Type-Safe: Full TypeScript-style type safety

πŸš€ Quick Start #

Installation #

Add to your pubspec.yaml:

dependencies:
  flutter_awesome_notification: ^0.0.2

Basic Setup #

import 'package:flutter/material.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:flutter_awesome_notification/flutter_awesome_notification.dart';
import 'firebase_options.dart';

void main() async {
  WidgetsFlutterBinding.ensureInitialized();

  // Initialize the notification plugin BEFORE Firebase
  await FlutterAwesomeNotification.initialize(
    config: FlutterFlutterAwesomeNotificationConfig(
      firebaseOptions: DefaultFirebaseOptions.currentPlatform,
      mainChannelId: 'my_app_notifications',
      mainChannelName: 'My App Notifications',
      onNotificationTap: (data) {
        print('Notification tapped: $data');
      },
      onNavigate: (pageName, id, data) {
        print('Navigate to: $pageName with id: $id');
      },
    ),
  );

  // Initialize Firebase
  await Firebase.initializeApp(
    options: DefaultFirebaseOptions.currentPlatform,
  );

  runApp(MyApp());
}

That's it! You now have full notification support with just a few lines of code.

πŸ“– Configuration #

Complete Configuration Example #

await FlutterAwesomeNotification.initialize(
  config: FlutterFlutterAwesomeNotificationConfig(
    // REQUIRED
    firebaseOptions: DefaultFirebaseOptions.currentPlatform,

    // Channel Configuration
    mainChannelId: 'my_app_channel',
    mainChannelName: 'My App Notifications',
    mainChannelDescription: 'General notifications',
    notificationIcon: '@mipmap/ic_launcher',

    // Callbacks
    onNotificationTap: (data) {
      // Handle notification tap
      print('Tapped: $data');
    },
    onNavigate: (pageName, id, data) {
      // Custom navigation
      // Example: GoRouter.of(context).push('/$pageName/$id');
    },
    getCurrentUserId: () {
      // Return current user ID for filtering
      return userCubit.getUserModel()?.id;
    },
    customFilter: (messageData) async {
      // Custom filtering logic
      // Return true to show, false to hide
      return true;
    },
    
    // Logging Options
    
    // Option 1: External logger (recommended - unified logging)
    // Compatible with flutter_awesome_logger and other logging solutions
    externalLogger: logger, // Your logger instance with d(), i(), w(), e() methods
    
    // Option 2: Logger callback (legacy support)
    // logger: (message, {error}) {
    //   myLogger.log(message, error: error);
    // },

    // Filtering Options
    enableActionStepFiltering: true,
    enableChatRoomFiltering: true,
    isActiveChatRoom: (chatRoomId) {
      // Check if user is currently in this chat room
      return appCubit.isActiveChatRoom(chatRoomId);
    },
    chatPageRoute: 'chat-page',

    // Notification Types
    notificationTypeToPage: {
      'action_step': 'challenge-details',
      'chat_message': 'chat-room',
      'event_reminder': 'event-details',
    },

    // Advanced
    enableLogging: true,
    requestPermissionOnInit: true,
    showAlertInForeground: true,
    showBadgeInForeground: true,
    playSoundInForeground: true,
    defaultNotificationTitle: 'New Update',
    defaultNotificationBody: 'You have a new update',
    environment: 'production',
  ),
);

Minimal Configuration #

For a basic setup, only Firebase options are required:

await FlutterAwesomeNotification.initialize(
  config: FlutterFlutterAwesomeNotificationConfig(
    firebaseOptions: DefaultFirebaseOptions.currentPlatform,
  ),
);

🎯 Usage #

Access the Service #

final notificationService = FlutterAwesomeNotification.instance;

Topic Subscriptions #

// Subscribe to a topic
await notificationService.subscribeToTopic('announcements');

// Unsubscribe from a topic
await notificationService.unsubscribeFromTopic('announcements');

Get FCM Token #

final token = await notificationService.getDeviceToken();
print('FCM Token: $token');

Show Local Notification #

await notificationService.showLocalNotification(
  id: 123,
  title: 'Hello!',
  body: 'This is a local notification',
  data: {'key': 'value'},
);

Schedule Notification #

await notificationService.scheduleNotification(
  id: 124,
  title: 'Reminder',
  body: 'Don\'t forget to check this!',
  scheduledDate: DateTime.now().add(Duration(hours: 2)),
  data: {'reminder_type': 'task'},
);

Cancel Notifications #

// Cancel specific notification
await notificationService.cancelNotification(123);

// Cancel all notifications
await notificationService.cancelAllNotifications();

Check Notification Permissions #

final enabled = await notificationService.areNotificationsEnabled();
if (!enabled) {
  await notificationService.requestPermissions();
}

Unified Logging with External Logger #

The plugin supports external logger instances for unified logging across your app:

// 1. Create or use your existing logger instance
class MyLogger {
  void d(String message) => print('πŸ” DEBUG: $message');
  void i(String message) => print('ℹ️ INFO: $message');
  void w(String message) => print('⚠️ WARNING: $message');
  void e(String message, {dynamic error, StackTrace? stackTrace}) {
    print('❌ ERROR: $message');
    if (error != null) print('Error: $error');
  }
}

final logger = MyLogger();

// 2. Pass it to the plugin during initialization
await FlutterAwesomeNotification.initialize(
  config: FlutterAwesomeNotificationConfig(
    firebaseOptions: DefaultFirebaseOptions.currentPlatform,
    enableLogging: true,
    externalLogger: logger, // 🎯 Your logger instance
  ),
);

Benefits:

  • βœ… Unified logging across all plugins (deeplink, notification, etc.)
  • βœ… Compatible with flutter_awesome_logger and other logging solutions
  • βœ… Consistent log format and filtering
  • βœ… No need for custom callbacks

Supported Log Levels:

  • d() - Debug messages (initialization, state changes)
  • i() - Info messages (successful operations)
  • w() - Warning messages (non-critical issues)
  • e() - Error messages (failures, exceptions)

πŸ” How It Works #

App State Behavior #

Foreground (App Open & Visible)

  1. FCM Message Received β†’ FirebaseMessaging.onMessage stream
  2. Custom Filtering Applied β†’ Action steps, chat rooms, user filtering
  3. Local Notification Shown β†’ Via flutter_local_notifications plugin
  4. Tap Navigation β†’ onNavigate callback with pageName and id

Background (App Minimized)

  1. FCM Message Received β†’ System notification (if notification field present)
  2. No Custom Filtering β†’ Plugin doesn't run in background
  3. User Taps Notification β†’ FirebaseMessaging.onMessageOpenedApp triggers
  4. Navigation on App Open β†’ Same onNavigate callback as foreground

Terminated (App Closed)

  1. FCM Message Received β†’ System notification (if notification field present)
  2. No Custom Filtering β†’ App not running
  3. User Taps Notification β†’ Cold app launch with initial message
  4. Navigation on Launch β†’ FirebaseMessaging.getInitialMessage() β†’ onNavigate

Key Differences by App State #

Feature Foreground Background Terminated
Custom Filtering βœ… Full ❌ None ❌ None
Notification Display βœ… Plugin βœ… System βœ… System
Navigation βœ… Immediate βœ… On tap βœ… On launch
Plugin Processing βœ… Active ❌ Dormant ❌ Dormant

FCM Payload Requirements #

For Background/Terminated delivery:

{
  "notification": {
    "title": "New Message",
    "body": "You have a new message"
  },
  "data": {
    "pageName": "chat-room",
    "id": "room123",
    "type": "message"
  }
}

⚠️ Data-only payloads won't show in background/terminated:

// ❌ Won't show in background/terminated
{
  "data": {
    "pageName": "chat-room",
    "id": "room123"
  }
}

Filtering System #

The plugin provides multiple layers of filtering:

  1. Action Step Filtering: Prevents users from seeing their own action notifications
  2. Chat Room Filtering: Hides notifications when user is in the chat room
  3. Custom Filtering: Your own logic via callback
  4. Type Filtering: Filter by notification type

πŸ”§ Migration from Existing Service #

If you're using the notification_service/ from challenge_app, here's how to migrate:

Before (Old Code) #

// In main.dart
NotificationService.registerBackgroundMessageHandler();
await Firebase.initializeApp();

// In your app
await getIt<NotificationService>().initialize();

After (Plugin) #

// In main.dart
await FlutterAwesomeNotification.initialize(
  config: FlutterAwesomeNotificationConfig(
    firebaseOptions: DefaultFirebaseOptions.currentPlatform,
    onNotificationTap: (data) => AutoNavigation.handleNotificationTap(data),
    getCurrentUserId: () => getIt<UserCubit>().getUserModel()?.id,
    isActiveChatRoom: (id) => getIt<MyAppCubit>().isActiveChatRoom(id),
    chatPageRoute: RouteNames.chatPage,
    logger: (msg, {error}) => logger.d(msg, error: error),
  ),
);
await Firebase.initializeApp();

// That's it! No need for separate initialization

Example: my_bottom_nav_bar.dart #

Future<void> _initializeServices() async {
  logger.i('MyBottomNavBar: Initializing services');
  
  try {
    final notificationService = FlutterAwesomeNotification.instance;

    // Optional: Subscribe to topics
    // await notificationService.subscribeToTopic('challenges');
    
    logger.i('MyBottomNavBar: Services initialized');
  } catch (e) {
    logger.e('MyBottomNavBar: Error initializing services', error: e);
  }
}

πŸ“± Server-Side Configuration #

FCM Message Format #

For proper filtering, send data-only messages:

{
  "data": {
    "type": "action_step_completion",
    "excludeUserId": "user123",
    "challengeId": "challenge456",
    "pageName": "challenge-details",
    "id": "challenge456",
    "title": "Challenge Update",
    "body": "Someone completed a step!"
  },
  "token": "fcm_device_token"
}

πŸ› Troubleshooting #

Notifications Not Showing #

Foreground Issues:

  1. Check if permissions are granted:
    final enabled = await notificationService.areNotificationsEnabled();
    
  2. Ensure plugin is initialized before Firebase initialization
  3. Check if custom filters are blocking notifications

Background/Terminated Issues:

  1. Critical: FCM payload must include notification field:
    {
      "notification": {"title": "Title", "body": "Body"}, // REQUIRED
      "data": {"pageName": "route"}
    }
    
  2. Data-only payloads won't show in background/terminated states
  3. Custom filtering doesn't work in background/terminated
  1. Verify onNavigate callback is set
  2. Ensure pageName is in notification data
  3. Check navigation implementation in callback

πŸ“Š Comparison #

Feature flutter_awesome_notification Manual Setup
Setup Complexity ⭐️ Simple ⭐️⭐️⭐️⭐️ Complex
Lines of Code ~10 lines ~500+ lines
Filtering System βœ… Built-in ❌ Manual
Topic Management βœ… Built-in ❌ Manual
Documentation βœ… Complete ❌ Variable
Maintenance βœ… Plugin updates ❌ Manual updates

πŸ“„ License #

MIT License - see LICENSE file for details

🀝 Contributing #

Contributions are welcome! Please open an issue or submit a PR.

πŸ“ž Support #

For issues, questions, or feature requests, please open an issue on GitHub.

0
likes
120
points
22
downloads

Publisher

unverified uploader

Weekly Downloads

A comprehensive notification plugin for Flutter with FCM, local notifications, and intelligent filtering.

Repository (GitHub)
View/report issues

Documentation

API reference

License

MIT (license)

Dependencies

firebase_core, firebase_messaging, flutter, flutter_local_notifications, plugin_platform_interface, timezone

More

Packages that depend on flutter_awesome_notification

Packages that implement flutter_awesome_notification