firebase-ios-sdk
firebase-ios-sdk copied to clipboard
FR: Update iOS 16 Live Activities using FCM
Feature proposal
- Firebase Component: Cloud Messaging
Apple just added iOS 16 Live Activities to Xcode 14 Beta 4: https://developer.apple.com/documentation/activitykit/displaying-live-data-on-the-lock-screen-with-live-activities
Updating a Live Activity is done using remote push notifications (see "Update or end a Live Activity with a remote push notification" in the documentation). Each active Live Activity gets its own push token and is updated whenever a remote notification is sent to that token with the app-specific payload, e.g.
{
"aps": {
"timestamp": 1650998941,
"event": "update",
"content-state": {
"driverName": "Anne Johnson",
"estimatedDeliveryTime": 1659416400
}
}
}
Currently, FCM maps the APNS device token to its own registration token. It would be great to use FCM to also send pushes to the Live Activities of an app. Is there a way to use FCM to send an Apple remote notification to a specific APNS token (instead of using a FCM registration token)?
Adding for consideration to the Firebase 10 milestone.
cc: @leojaygoogle
Are there any updates on the fix for this?
We are still investigating a Live Activities and FCM integration. In the meantime, if you have any feedback or suggestions please feel free to follow up.
If you can share the kind of integration you are considering, that would be helpful for us to ensure that we consider all the different use cases.
@aashishpatil-g we are working on Taxi.eu, a taxi booking app and would like to use Live Activities to show the user the status of the ride (approaching taxi, ...). FCM is used for all push related things and we are sending push notifications for each status change. We would like to keep using FCM for Live Activities as well but would need support to send a notification to a specific push token.
For us, it would be fine to just send the custom APNS push token with the push payload and FCM would send the push notification to that specific token and not the user's general FCM token.
Anyone think of a workaround for this?
Would love to see a workaround for this without having to set up our own apns stuff!
Thanks for the interest @ericagredo and @Hawki101. We are still investigating this.
If live activity support is important for you, please be sure to give a thumbs up to the original post if you haven't done so already.
I attempted a workaround today generating the fcm token on the server, however, ran into Invalid [apns-push-type] set for apns platform
for "apns-push-type": "liveactivity"
so wasn't able to use this as a way around!
I have a working workaround. It’s using Firebase functions. I’ll post a write up tomorrow for everyone.
Epic! currently working on a direct send via APNS instead! but interested to read through some alternatives!
I have a working workaround. It’s using Firebase functions. I’ll post a write up tomorrow for everyone.
To begin, you want to make sure you've gone through the process of enabling push notifications and downloaded the p8 file. https://medium.com/@syumak/how-to-send-push-notifications-to-ios-devices-via-p8-key-using-amazon-pinpoint-f08efb2a6b7 Then, create a firebase function. In our function we're going to be using the http2
and jsonwebtoken
library. Here is my code with what you need:
app.post("/startTrigger", async (request, response) => {
var amount = request.body.amount
var deviceToken = request.body.deviceToken;
var privateKey = fs.readFileSync('YOUR_P8_FILE.p8');
const secondsSinceEpoch = Math.round(Date.now() / 1000)
var payload = {
iss: 'YOUR_TEAM_ID',
iat: secondsSinceEpoch
}
var finalEncryptToken = jwt.sign(payload, privateKey, {algorithm: 'ES256', keyid: 'YOUR_KEY_ID'});
const session = http2.connect('https://api.sandbox.push.apple.com:443/3/device/' + deviceToken);
const body = {
"aps": {
"timestamp": secondsSinceEpoch,
"event": "update",
"content-state": {
'value': amount
}
}
};
functions.logger.log("token:", finalEncryptToken);
var buffer = new Buffer.from(JSON.stringify(body));
const req = session.request({
":method": "POST",
":path": "/3/device/" + deviceToken,
"authorization": "bearer " + finalEncryptToken,
"apns-push-type": "liveactivity",
"apns-topic": "YOUR_BUNDLE_ID.push-type.liveactivity",
"Content-Type": 'application/json',
"Content-Length": buffer.length
});
functions.logger.log()
req.on('response', (headers) => {
console.log(headers[http2.constants.HTTP2_HEADER_STATUS]);
});
let data = '';
req.setEncoding('utf8');
req.on('data', (chunk) => data += chunk);
req.on('end', () => {
console.log(`The server says: ${data}`);
});
req.end(JSON.stringify(body));
};
When you create your p8 file, you'll see that you get the file but on the page you downloaded it they'll also give you a KEY ID. That's what you use to fill in for KEY_ID. "YOUR_P8_FILE" is the path to your downloaded p8 file. My p8 file was deployed with my function. You also need your team ID, which you get from the developer page and should be under your name. Device token is the activity push token that your activity produces. You need to send that to the function as a post request. Follow this guide as well to make sure you have the payload just like your content state https://developer.apple.com/documentation/activitykit/update-and-end-your-live-activity-with-remote-push-notifications
I have a working workaround. It’s using Firebase functions. I’ll post a write up tomorrow for everyone.
To begin, you want to make sure you've gone through the process of enabling push notifications and downloaded the p8 file. https://medium.com/@syumak/how-to-send-push-notifications-to-ios-devices-via-p8-key-using-amazon-pinpoint-f08efb2a6b7 Then, create a firebase function. In our function we're going to be using the
http2
andjsonwebtoken
library. Here is my code with what you need:app.post("/startTrigger", async (request, response) => { var amount = request.body.amount var deviceToken = request.body.deviceToken; var privateKey = fs.readFileSync('YOUR_P8_FILE.p8'); const secondsSinceEpoch = Math.round(Date.now() / 1000) var payload = { iss: 'YOUR_TEAM_ID', iat: secondsSinceEpoch } var finalEncryptToken = jwt.sign(payload, privateKey, {algorithm: 'ES256', keyid: 'YOUR_KEY_ID'}); const session = http2.connect('https://api.sandbox.push.apple.com:443/3/device/' + deviceToken); const body = { "aps": { "timestamp": secondsSinceEpoch, "event": "update", "content-state": { 'value': amount } } }; functions.logger.log("token:", finalEncryptToken); var buffer = new Buffer.from(JSON.stringify(body)); const req = session.request({ ":method": "POST", ":path": "/3/device/" + deviceToken, "authorization": "bearer " + finalEncryptToken, "apns-push-type": "liveactivity", "apns-topic": "YOUR_BUNDLE_ID.push-type.liveactivity", "Content-Type": 'application/json', "Content-Length": buffer.length }); functions.logger.log() req.on('response', (headers) => { console.log(headers[http2.constants.HTTP2_HEADER_STATUS]); }); let data = ''; req.setEncoding('utf8'); req.on('data', (chunk) => data += chunk); req.on('end', () => { console.log(`The server says: ${data}`); }); req.end(JSON.stringify(body)); };
When you create your p8 file, you'll see that you get the file but on the page you downloaded it they'll also give you a KEY ID. That's what you use to fill in for KEY_ID. "YOUR_P8_FILE" is the path to your downloaded p8 file. My p8 file was deployed with my function. You also need your team ID, which you get from the developer page and should be under your name. Device token is the activity push token that your activity produces. You need to send that to the function as a post request. Follow this guide as well to make sure you have the payload just like your content state https://developer.apple.com/documentation/activitykit/update-and-end-your-live-activity-with-remote-push-notifications
@ericagredo This is awesome! So you just included your p8 file in the functions folder (e.g. next to index.js) & it will be uploaded & read just like that? I'm not really a Node dev so I don't know if that's how it will work. You also reference api.sandbox.push.apple.com
but I'm guessing we should use api.push.apple.com
for production? Sorry, I've never read all the APNs docs & don't know how much I can just copy/paste. Thanks again for posting your solution!
I have a working workaround. It’s using Firebase functions. I’ll post a write up tomorrow for everyone.
To begin, you want to make sure you've gone through the process of enabling push notifications and downloaded the p8 file. https://medium.com/@syumak/how-to-send-push-notifications-to-ios-devices-via-p8-key-using-amazon-pinpoint-f08efb2a6b7 Then, create a firebase function. In our function we're going to be using the
http2
andjsonwebtoken
library. Here is my code with what you need:app.post("/startTrigger", async (request, response) => { var amount = request.body.amount var deviceToken = request.body.deviceToken; var privateKey = fs.readFileSync('YOUR_P8_FILE.p8'); const secondsSinceEpoch = Math.round(Date.now() / 1000) var payload = { iss: 'YOUR_TEAM_ID', iat: secondsSinceEpoch } var finalEncryptToken = jwt.sign(payload, privateKey, {algorithm: 'ES256', keyid: 'YOUR_KEY_ID'}); const session = http2.connect('https://api.sandbox.push.apple.com:443/3/device/' + deviceToken); const body = { "aps": { "timestamp": secondsSinceEpoch, "event": "update", "content-state": { 'value': amount } } }; functions.logger.log("token:", finalEncryptToken); var buffer = new Buffer.from(JSON.stringify(body)); const req = session.request({ ":method": "POST", ":path": "/3/device/" + deviceToken, "authorization": "bearer " + finalEncryptToken, "apns-push-type": "liveactivity", "apns-topic": "YOUR_BUNDLE_ID.push-type.liveactivity", "Content-Type": 'application/json', "Content-Length": buffer.length }); functions.logger.log() req.on('response', (headers) => { console.log(headers[http2.constants.HTTP2_HEADER_STATUS]); }); let data = ''; req.setEncoding('utf8'); req.on('data', (chunk) => data += chunk); req.on('end', () => { console.log(`The server says: ${data}`); }); req.end(JSON.stringify(body)); };
When you create your p8 file, you'll see that you get the file but on the page you downloaded it they'll also give you a KEY ID. That's what you use to fill in for KEY_ID. "YOUR_P8_FILE" is the path to your downloaded p8 file. My p8 file was deployed with my function. You also need your team ID, which you get from the developer page and should be under your name. Device token is the activity push token that your activity produces. You need to send that to the function as a post request. Follow this guide as well to make sure you have the payload just like your content state https://developer.apple.com/documentation/activitykit/update-and-end-your-live-activity-with-remote-push-notifications
@ericagredo This is awesome! So you just included your p8 file in the functions folder (e.g. next to index.js) & it will be uploaded & read just like that? I'm not really a Node dev so I don't know if that's how it will work. You also reference
api.sandbox.push.apple.com
but I'm guessing we should useapi.push.apple.com
for production? Sorry, I've never read all the APNs docs & don't know how much I can just copy/paste. Thanks again for posting your solution!
yes for both questions. https://developer.apple.com/documentation/usernotifications/setting_up_a_remote_notification_server/sending_notification_requests_to_apns
Bump for supporting Live Activities via FCM, would really help with a feature we're working on.
@paulb777 👋🏼
@inkytibbs Make sure to upvote the OP at the top.
Bump for supporting Live Activities via FCM, would really help with a feature we're working on.
@paulb777 👋🏼
@inkytibbs why not just use firebase functions like I showed above? It works perfectly fine.
Bump for supporting Live Activities via FCM, would really help with a feature we're working on. @paulb777 👋🏼
@inkytibbs why not just use firebase functions like I showed above? It works perfectly fine.
We're going to give that solution a shot. Just thought it would be cool for FCM to officially support Live Activities with documentation and support (assuming Live Activities becomes a popular Apple API).
Thanks for sharing this workaround!
any news here @aashishpatil-g @paulb777 ?
FCM doesnt work with apns type = liveactivity in headers? @ericagredo Is there such a life hack with С# libs? may be you know?
It's really bad that FCM still doesn't have a plan to support live activity, and that we have to change a provider because of this, all other providers support it for months now.
Any update on this that i have missed?
Any news here @eldhosembabu ?
@here I am writing to inquire about your plans to support the new feature introduced in iOS 16 live activity. As a Firebase user, I am interested in utilising this feature in my app, and I would greatly appreciate it if Firebase could provide support for it. can you please guys give any timeline?
Sorry. We can't say anything about future plans on this feature. Please keep adding 👍 to help us with prioritization.
there's no progress on that yet?
Since Live Activities are expanding on the iOS ecosystem (iOS 17) it would totally make sense to bump up the prioritisation of this feature 😌 Would love to get an update on any plans 🙂
@here I fully understand that implementing new features takes time and effort. I want to express my unwavering trust in Firebase and its exceptional service. While I appreciate the ongoing commitment and value Firebase brings to my app's development, I kindly request any information you can provide regarding a potential timeline for the support of the 'live activity' feature. This will help me plan and align my app's roadmap accordingly. Thank you for your attention and ongoing commitment to improving Firebase. I look forward to any information or updates you can provide regarding the support for the "live activity" feature in iOS 16.
It's now over a year since this post was created. I would really love to see some updates from Firebase about this. Apple is really pushing this feature so it would be nice to have it supported.
++1
Please prioritize it!!
Based on previous comments the prioritization (partly) determined by a thumbs-up for the issue, although this has been the most requested feature for a long time, there is not even an update is shared.
To me, it seems like they don't want to lose users by bluntly saying, we don't want to implement or spend time on an iOS
only feature because we are Google
which makes sense, implementing this only helps iOS
because it will open the doors for a cool future. I guess until they come up with something like a temporary widget for Android
, this future is not going to be implemented.
I'd love to be wrong, please prove me wrong at any point.
PS: This comment is not about any individual or firebase itself. Merely a reality check for anyone who is waiting and eagerly checking this issue.