REST api authentication using firebase admin sdk - node.js

I have a REST api and the authentication is done using jwt tokens. To make may api more secure (users and authentication mechanism) I would like to use firebase authentication. I would like to know can we use firebase as a authentication server for my REST APIs.
My understanding is that the client app will send the username and password to the firebase server and they will provide a token. Using that token client app will send an api call to our server. I need to integrate firebase admin SDK in my server and validate the token using admin SDK to get the data from my database.
Please correct me when I am wrong.
Also, i have a concern that how to manage refresh tokens to keep my app logged in.
Please help me to integrate this in the right way, and I am using nodejs/expressjs to create the APIs.

can we use firebase as a authentication server for my REST APIs.
Yes, it's one of the services they provide: https://firebase.google.com/products/auth/
My understanding is that the client app will send the username and password to the firebase server and they will provide a token.
Correct. The usual Firebase auth is done entirely client side.
But if there is a specific auth mechanism you need such as LDAP/AD or some other form of enterprise shenanigans, then you would need to create your own tokens that the client will use to authenticate: https://firebase.google.com/docs/auth/admin/create-custom-tokens
Using that token client app will send an api call to our server.
Correct. Once the client has successfully logged in and retrieved their ID tokens, you on the server side need to verify the ID token: https://firebase.google.com/docs/auth/admin/verify-id-tokens via middleware.
Also, i have a concern that how to manage refresh tokens to keep my app logged in.
You need not worry about that so long as the client uses the appropriate method to retrieve the ID token. For example, on the Web side the client would call: https://firebase.google.com/docs/reference/js/firebase.User#getIdToken which states (emphasis mine):
Returns the current token if it has not expired, otherwise this will refresh the token and return a new one.
As you can see, the client side Firebase SDK handles everything for you. There is no need for you on the server side to keep track of ID tokens, refresh tokens, or anything really. All you need to do is verify the token, that's it.
Please see my previous answer for more details on server side verification: Firebase authentication using NodeJS

Related

How to authenticate user and send authenticated requests from client to server side in Firebase realtime database?

I have a client side React application which currently gets access of the current authenticated user through this:
const unsubscribe = onAuthStateChanged(auth, (user) => {
setCurrentUser(user);
});
Also we have realtime database rules in certain parts like
request.auth != null
Now, I'm planning to shift the firebase part to a NodeJS + express server.
For this I have installed the firebase SDK in my server. But is it safe to use the normal authentication functions from firebase SDK?
In client side app, only one user object could exist at a particular time. Whereas, in the server side, there could be several requests for authentication at the same time.
Also, even if I do the authentication, how am I going to send authenticated requests to perform CRUD operations on my realtime and firestore databases?
Note: I've heard about the firebase-admin SDK, but have also learnt that it's immensely powerful. That's why I want to avoid using it. If I have to use it, what is the right way to do so?
The recommended approach is explained here in the Authentication doc.
And yes you need to use the Admin SDK on your Node.js backend server.
Basically the mechanism is the following one:
You keep the user authentication in your React app, in other word you call the Firebase Authentication service to sign in the user (with the JavaScript SDK from your web app). Firebase creates an ID token that uniquely identifies the user. See this section.
Then when the app interacts with your Node.js backend server you can send that ID token (a JWT) to your backend and validate it using the Firebase Admin SDK. The verifyIdToken() method is used to verify an ID token, as explained in this section. The method returns the decoded ID token from which you get the user's uid.
With the user's uid you can query your Realtime and Firestore databases for the data corresponding to the user (again with the Admin SDK).
IMPORTANT: Note that the Admin SDK totally bypasses security rules. So it's up to you, in your Node.js code, to manage the access to the data corresponding to the user.

How to create a secure API using Firebase Auth without installing Firebase SDK on the client

I'm trying to create an API for our app using Express.js endpoints that connect to our Firebase Cloud Firestore database. A main component of responding with the requested information securely is authentication, and we want to be able to make it as straight forward to the users as possible. For example, by them simply sending an API secret key on their requests.
My issue is that all of the authentication mechanisms that Firebase seem to provide require that the client is authenticated with the Firebase SDK, which would be uncomfortable for us to ask users to install.
In short, is there any way that they can either create a firebase token without the SDK or for us to authenticate them securely with an API key on our end? Note that the connection to our API would only be done through our user's back ends, never front end clients.
Thanks!
See:
https://firebase.google.com/docs/auth/admin/create-custom-tokens
Firebase gives you complete control over authentication by allowing you to authenticate users or devices using secure JSON Web Tokens (JWTs). You generate these tokens on your server, pass them back to a client device, and then use them to authenticate via the signInWithCustomToken() method.
To achieve this, you must create a server endpoint that accepts sign-in credentials—such as a username and password—and, if the credentials are valid, returns a custom JWT. The custom JWT returned from your server can then be used by a client device to authenticate with Firebase (iOS, Android, web). Once authenticated, this identity will be used when accessing other Firebase services, such as the Firebase Realtime Database and Cloud Storage. Furthermore, the contents of the JWT will be available in the auth object in your Firebase Realtime Database Security Rules and the request.auth object in your Cloud Storage Security Rules.
You can create a custom token with the Firebase Admin SDK, or you can use a third-party JWT library if your server is written in a language which Firebase does not natively support.

Check if user logged in from backend Firebase Authentication

In my frontend, the user logs in using Firebase Authentication Browser. That part works perfectly fine. In addition to Firebase backend, I also have NodeJS backend that serves additional content. However, I need to serve the content to only Authenticated user.
My question is: Is there a way for my NodeJS backend to know that a user has been authenticated when they make a request?
An authenticated client is issued an ID token that uniquely identifies the user. The client can get this this token using the provided API. Then, it can pass that token to external APIs, which is verify the token using the Admin SDK.

Restrict API access only for my authorized client applications

My client application is a SPA built with REACT-REDUX and back-end API is nodejs with express framework.
Problem is in my client application people can access information without login
so how to authenticate my client application without actually login to my server API.
I tried to use Auth0 but for Single page web application authentication is done only through login, there is an option for machine to machine but that is not suitable to my case because my client app is static web app no server to save client id.
i have studied few articles to get over from this most of them suggest implicit grant is suitable for my case if its true how to implement implicit grant in my client and server.
I have achieved this using JWT
Provide the client a JWT token on successful login which he will have to use in header every time he needs to use API.
then every other request use a middle-ware to verify this token, if valid let him continue or else send auth failed in response

Authentication flow with custom token for Firebase Authentication on cloud functions

I'm creating a game in which I would like to use firebase authentication using cloud functions for logging in and registering users. Since my dev platform (GameMaker Studio 2) doesn't have the firebase sdk, I've resulted in attempting to use the firebase auth restAPI. To authenticate a user, I have to at one point create a custom token using the users uID and then use that to login. The problem with this is that I can't really understand the flow of the authentication. How could the client have knowledge beforehand on it's userID from parameters such as email and password?
Any help in understanding the flow I need to authenticate a user will be greatly appreciated.
If you're developing on node.JS, you should be able to use npm to install the firebase package -- that would simplify things greatly.
Otherwise, the overall flow of authentication should look as follows.
Client gives email and password
Pass email & password to Firebase Authentication using your HTTP request. You should receive an auth token, and a uID if authentication was successful. (see here)
Now you have an id token that you can set as a cookie in your client's browser. You can verify this cookie by storing it in your backend for each subsequent GET request to your Node server.

Resources