laravel-notification-channels / fcm

Firebase Cloud Messaging (FCM) notifications channel for Laravel
https://laravel-notification-channels.com/
MIT License
495 stars 127 forks source link

How to handling error when token is expired #174

Closed Pangeranmw closed 1 year ago

Pangeranmw commented 1 year ago

Sorry for the question, i'm already follow the docs about handling errors here, but expired token is not deleted in my database..

Here is my code:

User model

   class User extends Authenticatable
    {
        use Uuids;
        use HasApiTokens, HasFactory, Notifiable;
        use SoftDeletes;
        use Notifiable;

        protected $guarded = ['id'];
        protected $hidden = [
            'pin',
            'password',
            'remember_token',
            'deleted_at',
        ];
        protected $casts = [
            'email_verified_at' => 'datetime',
        ];
        public function routeNotificationForFcm()
        {
            return $this->deviceToken()->pluck('device_token')->toArray();
        }
        public function deviceToken(){
            return $this->hasMany(DeviceToken::class);
        }
    }

Device Token Model (attribute 'device_token' and 'user_id')

    class DeviceToken extends Model
    {
        use HasFactory;
        protected $guarded = ['id'];
        public function user(){
            return $this->belongsTo(User::class);
        }
    }

DeleteExpiredNotificationTokens listener

    class DeleteExpiredNotificationTokens
    {
        public function handle(NotificationFailed $event): void
        {
            $report = Arr::get($event->data, 'report');

            $target = $report->target();

            $event->notifiable->notificationTokens()
                ->where('push_token', $target->value())
                ->delete();
        }
    }

this is how i send some notification:

    public function notifyDeliveryOrderCreated(){
        // notify admin, purchasing, admin gudang
        $notify = new DeliveryOrderCreated($this->id, $this->kode_do);
        foreach(User::allPurchasing() as $user){$user->notify($notify);}
        foreach(User::allAdminGudang() as $user){$user->notify($notify);}
        foreach(User::allAdmin() as $user){$user->notify($notify);}
        $this->logistic->notify($notify);
    }

Some of my Notification Class

    class DeliveryOrderCreated extends Notification
      {
        public $id;
        public $kode;

        //initializing values in this constructor
        function __construct($id, $kode) {
          $this->id = $id;
          $this->kode = $kode;
        }
        public function via($notifiable)
        {
          return [FcmChannel::class];
        }

        public function toFcm($notifiable)
        {
          return FcmMessage::create()
            ->setData([
              'intentValueId' => "deliveryOrderId",
              'intentKeyId' => "$this->id",
              'kode' => "$this->kode",
            ])
            ->setNotification(\NotificationChannels\Fcm\Resources\Notification::create()
              ->setTitle('Delivery Order Baru')
              ->setBody("Terdapat Delivery Order baru dengan kode $this->kode")
            )
            ->setAndroid(
                AndroidConfig::create()
                  ->setData([
                    'intentValueId' => "deliveryOrderId",
                    'intentKeyId' => "$this->id",
                    'kode' => "$this->kode",
                  ])
                  ->setNotification(AndroidNotification::create()
                  ->setClickAction("DeliveryOrderDetailActivity")
                )
            );
          }
      }

Do you have any advice?

Thanks

dwightwatson commented 1 year ago

The current readme shows how to handle expired tokens with dev-master. You should look at the docs for the current tagged release: https://github.com/laravel-notification-channels/fcm/tree/3.2.1

dwightwatson commented 1 year ago

Alternatively, you could use the latest 4.x beta and update your toFcm with the newer syntax:

$notification = new Notification(title: 'Delivery Order Baru', body: "Terdapat Delivery Order baru dengan kode $this->kode");

return (new FcmMessage(notification: $notification))
    ->data([
        'intentValueId' => "deliveryOrderId",
        'intentKeyId' => "$this->id",
        'kode' => "$this->kode",
    ])
    ->custom([
        'android' => [
            'data' => [
                'intentValueId' => "deliveryOrderId",
                'intentKeyId' => "$this->id",
                'kode' => "$this->kode",
            ],
        ],
    ]);
masterbater commented 1 year ago

The current readme shows how to handle expired tokens with dev-master. You should look at the docs for the current tagged release: https://github.com/laravel-notification-channels/fcm/tree/3.2.1

Current tag release doesnt have any docs for handle token removal?

dwightwatson commented 1 year ago

Apologies. Listen for the same event but the payload is different. Looks like you worked it out: https://github.com/laravel-notification-channels/fcm/issues/173#issuecomment-1765700672