I have a third party API that generates a token that lasts 60mins. I want to use the token to retrieve user information from the third party database which I want to save in Firestone so I can query later and take advantage of Firestore features like offline data persistence, notifications to specific user info, and analytics.
In order to generate this token, I give the input parameters of:
cardNumber (int)
PIN (int)
How do I create a Firestore user while using a third party API that generates a token? What’s the best way to go about copying the user information into the user on Firebase? Cloud function?
I couldn’t find any guides with flutter and am confused. Thanks!
Firebase Authentication ID tokens are JWTs that are signed with your Firebase project's credentials. In the case of custom authentication, you mint that token, and then sign in to Firebase with signInWithCustomToken.
If the third party API already delivers such a JWT signed with the correct key, it should work as is. More often the third party API will use a different format, and you will have to mint the JWT yourself using the Firebase Admin SDK or one of the third party libraries. Since this is a sensitive operation, it should only be done in a trusted environment, such as your development machine, a server you control, or Cloud Functions.
Related
I'm creating a Zapier Partner integration into my Firestore app.
I want Zapier to send data to Firestore.
It could go through a Firebase API.
Firestore data is structured relative to a users Id. I.e. /users/{userId}
What is the correct set of steps to ensure that a request from Zapier to store data in the API is for the correct user?
I assumed:
I need to add a OAuth 2.0 Client to my API section in Google Cloud (which gives me a ClientId and secret)
I need to unpack the token coming into the API to ensure that it relates to a valid user
Honestly OAuth2 plus the disparate technologies make it a bit fuzzy to see a clear path to implementation.
Many thanks.
I currently have a frontend (Swift, iOS) and backend (node.js) completely running. I am now looking into real time updates for certain parts of my application and I have decided to go with Firebase because it allows me to deploy quickly and scale easily later on.
However, as I already have an entire backend setup, which authenticates the user and sends back a token (JWT), I would like to know how I can use the same authentication for Firebase. The idea would be to set custom rules in Firebase based on the userID, and to use this userID (which is just a regular id, e.g. my userID is 1, not a UUID) to create collections inside the real time database and Firestore.
I have already read the docs on custom tokens, but I am left with a couple of concerns:
Can I use this to sign a user in, without using Firebase Auth? Or will this create a user in Firebase Auth too?
I can only sign the JWT with an expiry for max. 60 mins from now, so one hour. Would this mean I have to re-authenticate every hour? How should I go about this? My current app grants a JWT which is valid for 21 days.
Should I use the same JWT for Firebase as I use for my entire application, or should I generate a new one and send this one back too, with the main purpose to use it for Firebase Auth in my Swift application?
The JWT needs to be generated with a different set of keys provided by Google in order for Firebase to verify the JWT. You can't use your existing JWT which was signed by another set of keys on your existing server.
But what you could do is use your existing user ids and sign them with Google's keys at the same time when signing the keys for your existing system and end up with 2 JWTs which you pass to your client.
If I share a user's Firebase device ID key (for a user who has my app installed) with other Firebase service providers, can they send messages from their account (using their authentication key) to a user who has my app installed?
Yes I do realize the process of sharing a user's Firebase device ID key could be problematic. The problem I am trying to solve is that I want multiple providers to be able to send messages to a user who has my app installed.
The Firebase Instance ID (also known as a registration token, or FCM token) identifies an installation of your app on a specific device.
Sending messages to such tokens in a project always requires an additional form "authentication.
The Firebase Cloud Messaging versioned REST API requires that the user has a service account. If you create a service account for each of your service providers, you grant them complete access to your Firebase project. So they can't only send FCM messages, they can also access every other Firebase product: e.g. delete your database, read all your users, etc.
The legacy REST API for Firebase Cloud Messaging instead uses a Server Key to authorize its callers. If you share your FCM server key with other service providers, they can only send FCM messages with that key. But they can send whatever messages they want to whatever user.
You might want to consider setting up your own API endpoint on Cloud Functions for Firebase. That way you can determine yourself how to secure that API, and what you allow your service providers to send to what users of your app.
Assuming that the Firebase Device ID Key you're referring to is the FCM Registration token, then having the value alone won't enable others to send a message to it without the corresponding Server Key it is associated with.
For your use-case of allowing multiple senders to a single app, you could refer to the official documentation on Receiving messages from multiple senders. I believe my answer here could also be helpful.
Referring to - https://developers.google.com/actions/identity/oauth2-code-flow Im using Actions SDK which implies Im using Firebase Functions for the fulfillment handling.
Im storing information in Firebase against the UID I got from FirebaseUser.getUid() in an Android app. So far so good.
I've setup a mock OAuth2.0 server and this seems to be happy exchanging tokens.
However later on in the documentation it states:
"Your service's API endpoints use the access token to identify the user on whose behalf Google is making the API call, and to verify that Google has authorization to access the endpoint on the user's behalf."
My fulfillment however is in Firebase Functions. So...
Do I need to get my FirebaseFunction to get the User ID from the OAuth2.0 server? Do I need to setup an OAuth2.0 server in Firebase Functions? Where does the OAuth2.0 server sit? And how do I get my Firebase Function to get the same User ID as reported by Android?
First - you're starting with a small misconception. Actions on Google and the Actions SDK do not require Firebase Functions for fulfillment. Firebase Functions do make it easier - they provide the publicly accessible HTTPS endpoint that you need for a webhook, but if you have your own server (with valid SSL certificate) or if you want to use AWS Lambda or something similar, you can certainly do so. And if you want to use a language besides JavaScript, the JSON protocol used is documented (although sometimes not clearly).
To answer your questions:
If you need the UserID in your webhook, then yes, it needs some way to get that UserID given the access token it will be handed. But how you do this depends on how you implemented your OAuth server and token. For example:
If you used signed JTWs as your token, then the UserID is part of the JWT and all your webhook needs to do is extract this and verify the signature and timeframe on the JWT are valid. You don't need to contact any other server to do this.
If you're storing the tokens and corresponding user info in Firebase or in some other database or data store - just read the token from your webhook!
You certainly can create another HTTPS endpoint you can use to validate the token and get the info from it - this is what Google does, for example.
Your OAuth server does not need to live in Firebase Functions any more than your webhook does. It might be a good place for it to live (along with the authentication page on Firebase Hosting), but it isn't required.
Your OAuth server can sit... anywhere. Well, anywhere public on the Internet with a valid SSL certificate anyway.
This last point is exactly what account linking is all about. You need to make sure that, when they authenticate against your server, you get the UserID that is "reported by Android", whatever that means in your context (but see my update below). Once you have this UserID, you need to make sure it gets associated against any of the tokens that you issue for this user, and you need to provide a way for your service to get this UserID from the token.
How you do this is up to you, and depends on the rest of your architecture and what you're trying to do with it. The Google Assistant doesn't care - it has its own notion of a UserId which is separate from yours, so to identify the user with your UserId, you'll use the token that it hands you.
Update
You raise a good point in the comments about the statement "The user ID on Android devices will also be the same as the user ID on a Google Home". This is true, but talks about the anonymous cookie-like UserID that is available through the Assistant platform only (which is why it is in the section on Anonymous User Identity). It doesn't talk about any ID that you can get through other Android apps. To associate the ID you get through other apps to the Assistant's ID, you need to use Account Linking as described on the following page.
If all you need is a consistent way to track a user that visits your Action multiple times, and you want that to be consistent on any Assistant platform (Google Home, Assistant for Android, or Assistant for iOS), then you just need to use the UserID that is provided through the API/JSON. You don't need Account Linking or an OAuth server. But this is not a Google ID or the Firebase ID, it is a anonymous UserID that is valid on the Assistant platforms only (and then, only within certain conditions if the user does not reset it).
Update 2 To be clear about OAuth and JWTs:
You ask in the questions "Where else can I get the JWT?"
In short - you build it yourself.
Remember that, if you are providing an OAuth server, one of the things you need to do is to issue auth tokens and refresh tokens. Those tokens can be anything you want - the only criteria is that your webhook be able to take the token and, somehow, get the information it needs out of it that ties it to a user.
But you are responsible for putting that information in there in the first place.
So when the user logs in during account linking, you might use Firebase Authentication to log them in. Once you've done so, you can get a Firebase ID and/or a Google ID for them. (After all, they've logged into your OAuth web page - you have to know something about them.)
After they log in, you're redirecting them to some place Google has asked you to, and you're including a token as part of that. That token can be the JWT that you're creating, and in that JWT, you can include the ID information you have from their login.
(And, again... it doesn't have to be a JWT. It can be anything you want. The only requirement is that you be able to validate it and use it to get the information you need.)
I use Firebase to store real time status updates for an app. I have my own authentication system for logging users in. I would like to share the data I store on Firebase to vendors who use our API, but I want to make sure they have only read access to our data.
From what I've read, it seems like securing data by user must be done through Firebase's own authentication system. Is there a way to do this without using their authentication system (maybe through a token system)?
You can definitely generate Firebase tokens in your application code, with custom properties that may be subsequently used in the Firebase security rules. Take a look at Generating a Secure Token in the Firebase docs.
Also see Can a Firebase Security Rule check if someone has specific access rights?, where #Frank van Puffelen offered a more comprehensive role-based approach.
I ended up using a system where a vendor calls one of my APIs (protected by my own internal authorization system) that returns a token that the user can use to authenticate with Firebase.
I use PHP and there is a token generator written by the Firebase team here. Don't forget the JWT PHP library this token generator relies on.
The token generator takes what is called a Firebase secret (you can find this in your particular Firebase instance page) passed into its class constructor and returns a random token based on this secret.