How do I use the local Firebase Auth emulator and not production auth to test my users? - firebase-authentication

My app still expects to validate users with the production firebase-auth instance, despite having initialised the auth emulator locally with:
firebase init emulators
This is the auth logic in my React app:
const handleLogin = () =>
authentication.signInWithEmailAndPassword("emulator#test.com", "emulator");
After handleLogin is triggered, I get the error "auth/user-not-found" as firebase is querying the production auth instance instead.

You need to call useEmulator synchronously, right after initialisation of your app’s auth instance. useEmulator takes the local emulator URL as its only argument.
You need the following wherever your firebase auth instance is initialised:
Firebase SDK Version 9 with tree shaking
import { getAuth, connectAuthEmulator } from "firebase/auth";
const auth = getAuth();
connectAuthEmulator(auth, "http://localhost:9099");
Firebase SDK Version 8
import firebase from "./firebase-config";
import "firebase/auth";
const authentication = firebase.auth();
authentication.useEmulator("http://localhost:9099");
export default authentication;

Related

Insomnia auth0 stuck in authentication loop

I'm trying to follow this guide to setup testing an express API in Insomnia. I have setup a poretected route at http://localhost:5000/api/v1/private/dashboard with express-openid-connect. I have also setup an machine-to-machine application and API in auth0.
When in Insomina I try to access http://localhost:5000/api/v1/private/dashboard I am redirected to the universal login page. Trying to login does nothing. I don't think I've set this up right, but am strugging to understand the process and can't find a similar issue when searching.
I want to be able to make GET/POST/PUT/DELETE requests in Insomnia and the data be returned the same as unauthenticated routes.
I have tried various configuration changes including using client credentials, in body, using a different app type but I don't really understand auth0's configuration so don't know what I'm doing.
server.js (where the authenication check is called via oidc)
import express from "express";
import oidc from "express-openid-connect";
import publicRoutes from "./routes/publicRoutes.js";
import privateRoutes from "./routes/privateRotues.js";
const app = express();
const {
auth,
requiresAuth,
} = oidc;
const config = {
authRequired: false,
auth0Logout: true,
secret: process.env.SECRET,
baseURL: process.env.BASE_URL,
clientID: process.env.CLIENT_ID,
issuerBaseURL: process.env.ISSUER_BASE_URL,
};
console.log(config);
app.use(auth(config));
app.use("/api/v1/public", publicRoutes);
app.use("/api/v1/private", requiresAuth(), privateRoutes);
app.use("*", (req, res) => res.status(404).json({error: "File not found"}));
export default app;

Firebase Google Sign In not working in React Native

import firebase from 'firebase';
import React from 'react';
import { useAuthState } from 'react-firebase-hooks/auth';
import App from './testlogin';
import { View, Text, Button } from 'react-native';
import { firebaseConfig } from './firebaseConfig';
const app = firebase.initializeApp(firebaseConfig);
const auth = app.auth();
const db = app.firestore();
const googleProvider = new firebase.auth.GoogleAuthProvider()
export const signInWithGoogle = async () => {
try {
const res = await auth.signInWithPopup(googleProvider);
const user = res.user;
const query = await db
.collection("users")
.where("uid", "==", user.uid)
.get();
if (query.docs.length === 0) {
await db.collection("users").add({
uid: user.uid,
name: user.displayName,
authProvider: "google",
email: user.email,
});
}
} catch (err) {
console.error(err);
alert(err.message);
}
};
This code accesses the google sign in method and should pop up a window, but I don't get anything when I click the button. I have been having difficulty with implementing Firebase in React Native and this is one of the examples. I need an example of easy Google sign in button in React Native.
I recommend you to use https://rnfirebase.io/ library (their docs are quite helpful).
Here are their instructions for Google Sign-in: https://rnfirebase.io/auth/social-auth#google.
According to them, you need to
ensure the "Google" sign-in provider is enabled on the Firebase Console.
also install #react-native-google-signin/google-signin',
then "Before triggering a sign-in request, you must initialize the Google SDK using your any required scopes and the webClientId, which can be found in the android/app/google-services.json"
Finally, as because following:
Starting April 2020, all existing applications using external 3rd party login services (such as Facebook, Twitter, Google etc) must ensure that Apple Sign-In is also provided. - You would also need to support iOS / and Apple Sign-in too. (if are building app also for iOS).
NOTE: I also remember that I had to put both, SHA1 and SHA256 hashes in the Firebase Console as some Firebase services were not working without it.
How to find SHA hashes in Android for Firebase (signing with Keystore that will be used in production should be already configured):
The debug signing certificate is optional to use Firebase with your app, but is required for Dynamic Links, Invites and Phone Authentication. To generate a certificate run
cd android && ./gradlew signingReport
and copy the SHA1 and SHA256 from the debug key. This generates two variant keys. You can copy the 'SHA1' that belongs to the debugAndroidTest variant key option.
Again, I recommend you to put both SHA hashes in Firebase Console.

React Native with Google OpenID Connect

I am working on a react native application and I have some problems with OpenID connect. I would like to use some "Login with Google" functionality.
In normal (not native) react app I use the react-google-login library like this:
import { GoogleLogin} from 'react-google-login';
import axios from 'axios';
const CLIENT_ID = 'xxxxx.apps.googleusercontent.com';
const Login = () => {
const loginHandler = (response) => {
// I can use the OpenID JWT token got as response.tokenId e.g.
axios.get("/myapi", {
headers: {
Authorization: 'Bearer ' + response.tokenId
}
}).then(res => {
...
});
}
return (
<React.Fragment>
<GoogleLogin
clientId={CLIENT_ID}
buttonText='Login'
onSuccess={loginHandler}
cookiePolicy={'single_host_origin'}
responseType='code,token'
uxMode="redirect"
/>
</React.Fragment>
)
}
export default Login;
In the login handler as you can see I can use the OpenID JWT token and I can send it to the server.
I need the same in React Native but I haven't found any simple library for that. Neither of them returns the OpenID JWT token just the Oauth2 access token.
Does anybody have any idea which library I should use and how?
Thanks
Maybe you should use this library
npm install react-native-app-auth --savereact-native link react-native-app-auth
If you use yarn as a packet manager
yarn add #react-native-app-auth
Finally I managed to accomplish this with AppAuth

React Native app seems not being able to communicate with API

I have just generated a release APK of my React Native app and installed it in my device but it seems not being able to communicate with my API. If I run it through CLI using [react-native run-android] everything works fine but when it comes to the generated APK I can't even authenticate in the app.
I don't know if it has something to do with Secure Sockets Layer or even cors. I'll be pleased if you guys could help me out with it.
That's my app config:
import express from 'express';
import cors from 'cors';
import routes from './routes';
import './database';
class App {
constructor() {
this.server = express();
this.middlewares();
this.routes();
}
middlewares() {
this.server.use(cors());
this.server.use(express.json());
}
routes() {
this.server.use(routes);
}
}
export default new App().server;
Context Information:
APK installed in Galaxy S10 (android 10)
It could be better if you provided more information about your test environment (emulator) and the device you use for testing generated APK.
however, I guess it's a network security issue in new android versions, so take a look at this answer.

Using Firebase in Expo (React Native) app

I'm considering Firebase for my new mobile app which is an Expo app. Expo's team did a nice tutorial about it (https://docs.expo.io/versions/latest/guides/using-firebase/).
Reading this tutorial, I can see that the recommanded way is to put API credentials (key, project ID, etc.) directly in the app and initialize the client that way:
import * as firebase from 'firebase';
// Initialize Firebase
const firebaseConfig = {
apiKey: "<YOUR-API-KEY>",
authDomain: "<YOUR-AUTH-DOMAIN>",
databaseURL: "<YOUR-DATABASE-URL>",
storageBucket: "<YOUR-STORAGE-BUCKET>"
};
firebase.initializeApp(firebaseConfig);
The question: is it safe to put an API key in a RN (Expo) project?
im using firebase too , and along with that a lot other third party sdk which needs API KEy. I've done it by storing it in the backend, and when the App is initialized(i.e mounted),I call an API to backend whihc gives all the API keys , and I store them in respective Async storages, so that whenever i need that particular API key , i just do AsyncStorage.getItem('API_Key') , and it's both secured and cannot be tracked since it's from backend. And obviously in backend you want to store them as env variables. So i would suggest you to follow that.
In your case , just do
let firebaseApiKey = AsyncStorage.getItem('firebaseKey');
// Initialize Firebase
const firebaseConfig = {
apiKey: firebaseApiKey,
authDomain: "<YOUR-AUTH-DOMAIN>",
databaseURL: "<YOUR-DATABASE-URL>",
storageBucket: "<YOUR-STORAGE-BUCKET>"
};
firebase.initializeApp(firebaseConfig);
I'd recommend you use a service like Visual Studio App Center to define your env variables then reference those variables in your code. During the build process, VS App Center will fit in the values in places where you've used it in your code.
So the sensitive values never even touch your codebase. That's the safest solution I can think of.