Full Angular 7|8|9|10 Firebase Authentication Tutorial Examples Last updated on September 18, 2020 by Digamber

In this Angular tutorial, we are going to build full Angular 7|8|9|10 Firebase Authentication system from scratch using Firebase Real-time NoSQL cloud database.

Sign in with Google

Sign in with username/password

Sign up with email/password

Recover forget password

Send email verification to a newly created user

Protect or secure inner pages routes using CanActivate guard

Restrict access of non-authenticated users

Manage logged in state of Firebase user with LocalStorage This tutorial helps you cover the following topics:

Getting Started Before we go ahead, make sure you have Node JS set up on your local development machine. Install Angular CLI, Ignore if already installed. npm install -g @angular/cli Next, create Angular 10 application. Use the given below cmd to setup the Angular project. ng new angularfiebase-authentication Once the project is downloaded, get into the project directory. cd angularfirebase-authentication Install Bootstrap CSS Framework in Angular 10 application. npm install bootstrap Go to angular.json file and replace the given below code with “styles”: [ ] array. "styles" : [ "node_modules/bootstrap/dist/css/bootstrap.min.css" , "src/styles.css" ]

Install AngularFire2 Package I assume you have already created a Firebae project, if not then follow this tutorial How to setup a basic Firebase account and set up a Firebase Project? Install AngularFire2 package in Angular 10 app. npm install firebase @angular/fire --save Add your firebase configuration in enviorment.ts and enviorment.prod.ts files. export const environment = { production: false, firebase: { apiKey: "xxxxxxxx-xxxxxxxx" , authDomain: "xxxxxxxxxxxxxxxxxxxxxxxx" , databaseURL: "xxxxxxxxxxxxxxxxxxxxxxxx" , projectId: "xxxxxxxx" , storageBucket: "xxxxxxxx" , messagingSenderId: "xxxxxx" , appId: "xxxxx" , measurementId: "xxxxxxxxxxxxxxxx" } } ; Import and register AngularFire2 modules in app.module.ts. import { AngularFireModule } from "@angular/fire" ; import { AngularFireAuthModule } from "@angular/fire/auth" ; import { AngularFirestoreModule } from '@angular/fire/firestore' ; import { environment } from '../environments/environment' ; @ NgModule ( { imports : [ AngularFireModule . initializeApp ( environment . firebase ) , AngularFireAuthModule , AngularFirestoreModule , ] } )

Generate Angular Components In order to create a complete Angular 7|8|9|10 Firebase Authentication system, we need to generate angular components. ng g c components/dashboard ng g c components/sign-in ng g c components/sign-up ng g c components/forgot-password ng g c components/verify-email

Create Angular Routes Add following code in app-routing.module.ts file. import { NgModule } from '@angular/core' ; import { Routes , RouterModule } from '@angular/router' ; import { SignInComponent } from '../../components/sign-in/sign-in.component' ; import { SignUpComponent } from '../../components/sign-up/sign-up.component' ; import { DashboardComponent } from '../../components/dashboard/dashboard.component' ; import { ForgotPasswordComponent } from '../../components/forgot-password/forgot-password.component' ; import { AuthGuard } from "../../shared/guard/auth.guard" ; import { VerifyEmailComponent } from '../../components/verify-email/verify-email.component' ; const routes : Routes = [ { path : '' , redirectTo : '/sign-in' , pathMatch : 'full' } , { path : 'sign-in' , component : SignInComponent } , { path : 'register-user' , component : SignUpComponent } , { path : 'dashboard' , component : DashboardComponent } , { path : 'forgot-password' , component : ForgotPasswordComponent } , { path : 'verify-email-address' , component : VerifyEmailComponent } ] ; @ NgModule ( { imports : [ RouterModule . forRoot ( routes ) ] , exports : [ RouterModule ] } ) export class AppRoutingModule { } Enable the routes within view, add the following code in app.component.html file. < router-outlet > </ router-outlet >

Create Firebase Authentication Service Generate auth service and user interface files to create a Firebase authentication system with Angular 7|8|9/10. Create User Interface class. ng generate interface shared / services / user Go to shared/services/user.ts This user interface class is a schema for User object. export interface User { uid : string ; email : string ; displayName : string ; photoURL : string ; emailVerified : boolean ; } Create Auth Service This file holds the core logic of our authentication system. I’ll be covering up social login using Firebase’s Google auth provider. You can also create the login with Facebook, Twitter, and GitHub later on. The auth service will cover the sign-in with username/password, sign-up with sign-in with email/password, password reset, email verification, route protection using canActivate auth guard method. import { Injectable , NgZone } from '@angular/core' ; import { User } from "../services/user" ; import { auth } from 'firebase/app' ; import { AngularFireAuth } from "@angular/fire/auth" ; import { AngularFirestore , AngularFirestoreDocument } from '@angular/fire/firestore' ; import { Router } from "@angular/router" ; @ Injectable ( { providedIn : 'root' } ) export class AuthService { userData : any ; constructor ( public afs : AngularFirestore , public afAuth : AngularFireAuth , public router : Router , public ngZone : NgZone ) { this . afAuth . authState . subscribe ( user => { if ( user ) { this . userData = user ; localStorage . setItem ( 'user' , JSON . stringify ( this . userData ) ) ; JSON . parse ( localStorage . getItem ( 'user' ) ) ; } else { localStorage . setItem ( 'user' , null ) ; JSON . parse ( localStorage . getItem ( 'user' ) ) ; } } ) } SignIn ( email , password ) { return this . afAuth . auth . signInWithEmailAndPassword ( email , password ) . then ( ( result ) => { this . ngZone . run ( ( ) => { this . router . navigate ( [ 'dashboard' ] ) ; } ) ; this . SetUserData ( result . user ) ; } ) . catch ( ( error ) => { window . alert ( error . message ) } ) } SignUp ( email , password ) { return this . afAuth . auth . createUserWithEmailAndPassword ( email , password ) . then ( ( result ) => { this . SendVerificationMail ( ) ; this . SetUserData ( result . user ) ; } ) . catch ( ( error ) => { window . alert ( error . message ) } ) } SendVerificationMail ( ) { return this . afAuth . auth . currentUser . sendEmailVerification ( ) . then ( ( ) => { this . router . navigate ( [ 'verify-email-address' ] ) ; } ) } ForgotPassword ( passwordResetEmail ) { return this . afAuth . auth . sendPasswordResetEmail ( passwordResetEmail ) . then ( ( ) => { window . alert ( 'Password reset email sent, check your inbox.' ) ; } ) . catch ( ( error ) => { window . alert ( error ) } ) } get isLoggedIn ( ) : boolean { const user = JSON . parse ( localStorage . getItem ( 'user' ) ) ; return ( user !== null && user . emailVerified !== false ) ? true : false ; } GoogleAuth ( ) { return this . AuthLogin ( new auth . GoogleAuthProvider ( ) ) ; } AuthLogin ( provider ) { return this . afAuth . auth . signInWithPopup ( provider ) . then ( ( result ) => { this . ngZone . run ( ( ) => { this . router . navigate ( [ 'dashboard' ] ) ; } ) this . SetUserData ( result . user ) ; } ) . catch ( ( error ) => { window . alert ( error ) } ) } SetUserData ( user ) { const userRef : AngularFirestoreDocument < any > = this . afs . doc ( `users/ ${ user . uid } ` ) ; const userData : User = { uid : user . uid , email : user . email , displayName : user . displayName , photoURL : user . photoURL , emailVerified : user . emailVerified } return userRef . set ( userData , { merge : true } ) } SignOut ( ) { return this . afAuth . auth . signOut ( ) . then ( ( ) => { localStorage . removeItem ( 'user' ) ; this . router . navigate ( [ 'sign-in' ] ) ; } ) } } After that, go to app.module.ts file and import authentication service and pass the AuthService class into providers: [AuthService] array. By doing this our authentication service will be available throughout the application. import { AuthService } from "./shared/services/auth.service" ; @ NgModule ( { declarations : [ ... ] , imports : [ ... ] , providers : [ AuthService ] , bootstrap : [ ... ] } )

Create Angular Login with Firebase API It’s time to use AuthService class, It will help us creating Login authentication in Angular with Firebase. We will focus on: Sign-in with Username and Password

Sign-in with Gmail or Google auth We need to import AuthService into sign-in/sign-in.component.ts, then inject AuthService into the constructor. import { Component , OnInit } from '@angular/core' ; import { AuthService } from "../../shared/services/auth.service" ; @ Component ( { selector : 'app-sign-in' , templateUrl : './sign-in.component.html' , styleUrls : [ './sign-in.component.css' ] } ) export class SignInComponent implements OnInit { constructor ( public authService : AuthService ) { } ngOnInit ( ) { } } Place the following code inside the sign-in/sign-in.component.html file. < div class = " displayTable " > < div class = " displayTableCell " > < div class = " authBlock " > < h3 > Sign In </ h3 > < div class = " formGroup " > < input type = " text " class = " formControl " placeholder = " Username " #userName required > </ div > < div class = " formGroup " > < input type = " password " class = " formControl " placeholder = " Password " #userPassword required > </ div > < div class = " formGroup " > < input type = " button " class = " btn btnPrimary " value = " Log in " (click) = " authService.SignIn(userName.value, userPassword.value) " > </ div > < div class = " formGroup " > < span class = " or " > < span class = " orInner " > Or </ span > </ span > </ div > < div class = " formGroup " > < button type = " button " class = " btn googleBtn " (click) = " authService.GoogleAuth() " > < i class = " fab fa-google-plus-g " > </ i > Log in with Google </ button > </ div > < div class = " forgotPassword " > < span routerLink = " /forgot-password " > Forgot Password? </ span > </ div > </ div > < div class = " redirectToLogin " > < span > Don't have an account? < span class = " redirect " routerLink = " /register-user " > Sign Up </ span > </ span > </ div > </ div > </ div >

User Registration with Angular 10 Firebase Now, we will register the user with Angular and Firebae. Go to sign-up/sign-up.component.ts and add the code. import { Component , OnInit } from '@angular/core' ; import { AuthService } from "../../shared/services/auth.service" ; @ Component ( { selector : 'app-sign-up' , templateUrl : './sign-up.component.html' , styleUrls : [ './sign-up.component.css' ] } ) export class SignUpComponent implements OnInit { constructor ( public authService : AuthService ) { } ngOnInit ( ) { } } Go to sign-up/sign-up.component.html and add the code. < div class = " displayTable " > < div class = " displayTableCell " > < div class = " authBlock " > < h3 > Sign Up </ h3 > < div class = " formGroup " > < input type = " email " class = " formControl " placeholder = " Email Address " #userEmail required > </ div > < div class = " formGroup " > < input type = " password " class = " formControl " placeholder = " Password " #userPwd required > </ div > < div class = " formGroup " > < input type = " button " class = " btn btnPrimary " value = " Sign Up " (click) = " authService.SignUp(userEmail.value, userPwd.value) " > </ div > < div class = " formGroup " > < span class = " or " > < span class = " orInner " > Or </ span > </ span > </ div > < div class = " formGroup " > < button type = " button " class = " btn googleBtn " (click) = " authService.GoogleAuth() " > < i class = " fab fa-google-plus-g " > </ i > Continue with Google </ button > </ div > < div class = " formGroup " > < button type = " button " class = " btn facebookBtn " (click) = " authService.FacebookAuth() " > < i class = " fab fa-facebook " > </ i > Continue with Facebook </ button > </ div > </ div > < div class = " redirectToLogin " > < span > Already have an account? < span class = " redirect " routerLink = " /sign-in " > Log In </ span > </ span > </ div > </ div > </ div >

Angular 10 Forgot Password with Firebase We are going to create forgot password feature using Firebase in Angular. Go to forgot-password.component.ts add the code. import { Component , OnInit } from '@angular/core' ; import { AuthService } from "../../shared/services/auth.service" ; @ Component ( { selector : 'app-forgot-password' , templateUrl : './forgot-password.component.html' , styleUrls : [ './forgot-password.component.css' ] } ) export class ForgotPasswordComponent implements OnInit { constructor ( public authService : AuthService ) { } ngOnInit ( ) { } } Go to forgot-password.component.html add the code. < div class = " displayTable " > < div class = " displayTableCell " > < div class = " authBlock " > < h3 > Reset Password </ h3 > < p class = " text-center " > Please enter your email address to request a password reset. </ p > < div class = " formGroup " > < input type = " email " class = " formControl " placeholder = " Email Address " #passwordResetEmail required > </ div > < div class = " formGroup " > < input type = " submit " class = " btn btnPrimary " value = " Reset Password " (click) = " authService.ForgotPassword(passwordResetEmail.value) " > </ div > </ div > < div class = " redirectToLogin " > < span > Go back to ? < span class = " redirect " routerLink = " /sign-in " > Log In </ span > </ span > </ div > </ div > </ div >

Send Verification Email Firebase allows us to send verification email easily, add code in verify-email/verify-email.component.ts. import { Component , OnInit } from '@angular/core' ; import { AuthService } from "../../shared/services/auth.service" ; @ Component ( { selector : 'app-verify-email' , templateUrl : './verify-email.component.html' , styleUrls : [ './verify-email.component.css' ] } ) export class VerifyEmailComponent implements OnInit { constructor ( public authService : AuthService ) { } ngOnInit ( ) { } } Go to src/app/components/verify-email/verify-email.component.html and include the code. < div class = " displayTable " > < div class = " displayTableCell " > < div class = " authBlock " > < h3 > Thank You for Registering </ h3 > < div class = " formGroup " *ngIf = " authService.userData as user " > < p class = " text-center " > We have sent a confirmation email to < strong > {{user.email}} </ strong > . </ p > < p class = " text-center " > Please check your email and click on the link to verfiy your email address. </ p > </ div > < div class = " formGroup " > < button type = " button " class = " btn btnPrimary " (click) = " authService.SendVerificationMail() " > < i class = " fas fa-redo-alt " > </ i > Resend Verification Email </ button > </ div > </ div > < div class = " redirectToLogin " > < span > Go back to? < span class = " redirect " routerLink = " /sign-in " > Sign in </ span > </ span > </ div > </ div > </ div >

Use Route Guards to Protect Angular Routes Routes guards secure routes in Angular. Now, I will tell you how to easily secure routes from unauthorized access using canActivate() route guard method. Head over to auth.service.ts and look for the isLoggedIn() method. This function returns the boolean result to true when the user is logged-in. If user is not found then it will return false and doesn’t allow users to access the desired pages. get isLoggedIn ( ) : boolean { const user = JSON . parse ( localStorage . getItem ( 'user' ) ) ; return ( user !== null && user . emailVerified !== false ) ? true : false ; } We have to secure the inner pages, to get this functionality, we have to generate route guard files. Execute command to create route guards. ng generate guard shared / guard / auth Go to auth.guard.ts and place the code. import { Injectable } from '@angular/core' ; import { CanActivate , ActivatedRouteSnapshot , RouterStateSnapshot , Router } from '@angular/router' ; import { AuthService } from "../../shared/services/auth.service" ; import { Observable } from 'rxjs' ; @ Injectable ( { providedIn : 'root' } ) export class AuthGuard implements CanActivate { constructor ( public authService : AuthService , public router : Router ) { } canActivate ( next : ActivatedRouteSnapshot , state : RouterStateSnapshot ) : Observable < boolean > | Promise < boolean > | boolean { if ( this . authService . isLoggedIn !== true ) { this . router . navigate ( [ 'sign-in' ] ) } return true ; } } We have successfully secured application routes, now user needs to be authenticated before accessing app’s inner pages. Go to app-routing.module.ts and include route guard in angular routes. import { NgModule } from '@angular/core' ; import { Routes , RouterModule } from '@angular/router' ; import { SignInComponent } from '../../components/sign-in/sign-in.component' ; import { SignUpComponent } from '../../components/sign-up/sign-up.component' ; import { DashboardComponent } from '../../components/dashboard/dashboard.component' ; import { ForgotPasswordComponent } from '../../components/forgot-password/forgot-password.component' ; import { VerifyEmailComponent } from '../../components/verify-email/verify-email.component' ; import { AuthGuard } from "../../shared/guard/auth.guard" ; const routes : Routes = [ { path : '' , redirectTo : '/sign-in' , pathMatch : 'full' } , { path : 'sign-in' , component : SignInComponent } , { path : 'register-user' , component : SignUpComponent } , { path : 'dashboard' , component : DashboardComponent , canActivate : [ AuthGuard ] } , { path : 'forgot-password' , component : ForgotPasswordComponent } , { path : 'verify-email-address' , component : VerifyEmailComponent } ] ; @ NgModule ( { imports : [ RouterModule . forRoot ( routes ) ] , exports : [ RouterModule ] } ) export class AppRoutingModule { }