-
Notifications
You must be signed in to change notification settings - Fork 4.2k
Description
📜 Description
Context: novu/framework, in a Bridge app, when defining a workflow step of type "push"
Problem 1: push schema is limited to only two fields
The schema of a push step in (node_modules/@novu/framework/dist/esm/health-check.types-_.d.ts), is limited to only two fields: title and body. This is also the case in the dashboard when trying to create a push step.
But the schema also allows you to add provider objects with known provider fields, which leads to problem #2:
Problem 2: providerSchema for FCM might be outdated
For example, for FCM, you're allowed to pass a notification object among other fields, but it looks like the schema is outdated (not fully updated since the move to FCM HTTP V1?).
-
Notice that the providerSchemas for fcm does not have
fcmOptionsorfcm_optionsfield for example. -
See this line for example leading to a non-existent fcm docs page (404).
-
The provider schema doesn't have the fields of a real fcm notification object like AndroidConfig, WebpushConfig, etc.
Problem 3: You CANNOT override what Novu sends to FCM for Webpush.
When using the novu / framework (workflow as code) and defining a push step, no matter what you pass to novu as fields, Novu will still send only title + body. Any other values will just be ignored. Pass any other value and it will be ignored. Here, I'm referring to a native notification, not a data notification.
So, of course you can pass a data object and interpret it in your service worker, but this is HIGHLY unreliable since the quirks of iOS (webpush through PWA) will not always wake up the service worker, etc. Unreliable in chrome too.
So, the safest path for webpush is a standard notification.
But Novu will always send only title + body --> no Link! So when clicking the notification, the device doesn't know what to do. iOS will open the PWA without deep linking, Chrome will not always open the website. The device is confused: where to send the user?
Problem 4: Using Passthrough object to deep merge the body that Novu sends to FCM does not work
Using passthrough object is supposed to push extra fields in the request body does not work either. Novu will still send only title + body, no link, no fcmOptions, no icon, no badge, or anything like that.
Solution I ended up using: Creating a custom step and sending notifications to FCM myself
I had to build a custom step to be able to send standard webpush notifications through FCM. This is not ideal since it doesn't allow you to have proper novu logs, proper channel-based and per-workflow notification settings for users. Very hacky.
But it works! As soon as I did send directly through FCM, the full rich Webpush Notification reaches FCM which sends it to browsers in a RELIABLE way. iOS clicks on notifications is able to open a deep link, so does Chrome desktop, etc.
👟 Reproduction steps
dependencies:
- "@novu/framework": "^2.8.0"
- "novu": "^2.7.0"
In a bridge app, in a workflow definition, try adding a push step:
Here are the two exact shapes we tried inside the push step, both resulted in Firebase receiving only the plain notification.title/body (no data, no webpush, no fcmOptions), so the service worker never saw the rest of the payload.
1. Provider override (schema-compliant fields only):
await step.push('chat-msg-webpush', async () => ({
subject: 'New message',
body: 'Preview snippet',
data: {
actionUrl: 'https://example.com/chat/123',
chatId: '123',
workflow: 'chats_new_message',
subject: 'New message',
body: 'Preview snippet',
icon: 'https://cdn.example.com/avatar.png',
badge: 'https://cdn.example.com/badge.png',
tag: 'chat-msg-123',
chatTitle: 'Support',
},
}), {
providers: {
fcm: ({ outputs }) => ({
notification: {
title: outputs.subject,
body: outputs.body,
icon: outputs.data.icon,
badge: outputs.data.badge,
tag: outputs.data.tag,
},
data: outputs.data,
}),
},
});2. Provider override + _passthrough HTTP v1 envelope (to include webpush/fcmOptions):
await step.push('chat-msg-webpush', async () => ({
subject: 'New message',
body: 'Preview snippet',
data: {
actionUrl: 'https://example.com/chat/123',
chatId: '123',
workflow: 'chats_new_message',
subject: 'New message',
body: 'Preview snippet',
icon: 'https://cdn.example.com/avatar.png',
badge: 'https://cdn.example.com/badge.png',
tag: 'chat-msg-123',
chatTitle: 'Support',
},
}), {
providers: {
fcm: ({ outputs }) => ({
notification: {
title: outputs.subject,
body: outputs.body,
icon: outputs.data.icon,
badge: outputs.data.badge,
tag: outputs.data.tag,
},
data: outputs.data,
_passthrough: {
body: {
message: {
notification: {
title: outputs.subject,
body: outputs.body,
},
data: outputs.data,
webpush: {
notification: {
title: outputs.subject,
body: outputs.body,
icon: outputs.data.icon,
badge: outputs.data.badge,
tag: outputs.data.tag,
},
data: outputs.data,
fcmOptions: {
link: outputs.data.actionUrl,
},
},
fcmOptions: {
link: outputs.data.actionUrl,
},
},
},
},
}),
},
});👍 Expected behavior
Full rich notification reaching the service worker.
👎 Actual Behavior with Screenshots
Don't have screenshots but I can tell you I struggled with this for about 4 days.
In both cases, Novu reported “success,” but the actual payload that reached FCM (per the service worker) was just:
{
"notification": {
"title": "...",
"body": "..."
}
}Novu version
2.3.0
npm version
No response
node version
No response
📃 Provide any additional context for the Bug.
Feel free to tell me if this whole thing is a skill issue. I'd love to be able to send a full FCM standard notification through Novu for WebPush (and to Android / iOS app in the future). As of now, I'm sending calling FCM directly from the Bridge App in a Novu custom step.
👀 Have you spent some time to check if this bug has been raised before?
- I checked and didn't find a similar issue
🏢 Have you read the Contributing Guidelines?
- I have read the Contributing Guidelines
Are you willing to submit PR?
None