How to create an Authentication system in Vue.

How to create an Authentication system in Vue.

<span class="r"></span>

How to create an Authentication system in Vue.

Hey guys, today we are gonna look at how I created an authentication system using Vue and Firebase. Authentication is simply identifying an individual, usually based on a username or password before they can have access to a the data on your application.

Why use Vue

With over 154k stars on GitHub, Vue.js is currently the trendiest JavaScript front-end framework, beating Angular and React in GitHub star count by a fair margin. When it comes to overall popularity, React is still the king and Angular, thanks to its specificity, holds a solid place. But here in Nigeria, I don’t see much community behind Vue for a while now, and the developer community worldwide, too, seems to be following suit. So what is it about Vue that makes it gain more traction every month?

Vue might have started as a small project driven by developer needs of its creator, Evan You, but it has matured considerably over the years — becoming a full-fledged framework with a grownup ecosystem and developer tooling. Along the way, Vue attracted a decent number of contributors, sponsors, and evangelists.

What is Firebase?

In short terms, Firebase is a set of tools that allows you to develop an application without server-side programming. It has real-time database, authentication system, crash reporting, analytics and other services ready to use in your mobile/web app. That way, you can focus on your app and users.

For application with minimal back-end needs such as authentication or database storage, no need to re-invent the wheel, Firebase does it for you, and gives you much more tools. Also, you don’t need to bother about scaling, server performance and database size, Firebase scales everything automatically.

Shall we begin?

First, we are going to initialize a new Vue project by using the great tool Vue Cli 3 (github.com/vuejs/vue-cli).

If you don’t already have vue cli installed, let’s install it (This is done on your terminal — windows + R, then type CMD and press enter):

$ npm install -g @vue/cli</span>

Now that you have vue cli installed, let’s create a new project. In vue cli documentation, it say’s:

**Usage** $ vue create <project-name></span>

One of the cool features of Vue CLI 3, is that you can initialize your project with zero configuration required, so that you can start to code as fast as possible.

Let’s create our new Vue project and call it ‘vue-firebase-auth’. N/B: inside your CMD, go the folder you want to save your project. if you want your project to live on your documents folder. type cd/documents to enter the documents folder. Then type the command below.

$ vue create auth-system</span>

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1016/0*mWTba4fYE4lw3RSU.." width="508" height="166" role="presentation"/></noscript>

Scaffolding a Vue project

You will be prompted to pick a preset. You can either choose the default preset which comes with a basic Babel + ESLint setup, or select “Manually select features” to pick the features you need.

For our case, we are going to select “Manually select features” and choose vue-router optionsince we will be using it during this tutorial. For the other features, do as you want, as it won’t really matter for the rest of the tutorial.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1294/0*n_BFaK6B6NWBTE3x.." width="647" height="311" role="presentation"/></noscript>

Select the Router option

At the end, you will be asked if you want to save this preset for future projects and after that, and a couple of other questions, type n to reject, then press Enter. your project will be initialized.

Then, enter the new vue-firebase-tutorial directory, and run npm run serve

$ cd vue-firebase-tutorial
$ npm run serve</span>

Now, if you open the url ‘localhost:8080, you should have the default view of our Vue project!

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*eNgyIEuEcAycSxt0.." width="1400" height="735" role="presentation"/></noscript>

Vue New Project

The App Structure

Let’s have a quick look of the app structure.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/524/0*Vtf_69DYw6dljygB..." width="262" height="445" role="presentation"/></noscript>

App structure on VS CODE

The files we are gonna be working with are in the src folder

The other files are mostly configuration files generated by Vue Cli 3. If you want to have a complete overview of the structure, you can check the Vue Cli 3 documentation. Also, before going further in this tutorial, if you don’t already know the structure of a Vue file (like src/components/HelloWorld.vue), i advise you to take a look to this: https://vuejs.org/v2/guide/single-file-components.html

Now, lets get dirty…

Our app will consist of three views, two (Login view and Sign Up view) that we can access only without authentication, and one (Home view) that we can access only with authentication.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1148/0*urg69K7v3pY3_9au.." width="574" height="309" role="presentation"/></noscript>

App architecture

After login successfully or after a new account creation, we will be redirected to the part the needs authentication, the Home view.

Step One: Login and SignUp

1–1 The Login View

Let’s create the Login view. To do so, we will create a new Vue component called Login under src/views

For the moment, the component will simply consist of a title, two input fields, a button and a small sentence in the html.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*ig4K1qqgV0Ty8d-M.." width="1400" height="1017" role="presentation"/></noscript>

Login Component

Our component is now created! But how to display this new component in our app? Well, for that, we are going to use vue-router. Remember? We already installed it when we initialized the app with vue-cli.

What is vue-router ?

vue-router is the official router for [Vue.js](http://vuejs.org/). It deeply integrates with Vue.js core to make building Single Page Applications with Vue.js a breeze. Creating a Single-page Application with Vue.js + vue-router is dead simple. With Vue.js, we are already composing our application with components. When adding vue-router to the mix, all we need to do is map our components to the routes and let vue-router know where to render them.from vue-router documentation: [https://github.com/vuejs/vue-route](https://github.com/vuejs/vue-router)</span>

So, let’s add our new Logincomponent that we just created to our app router. Open the src/router.js file and add the Logincomponent to the router like that:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*Mj-1XqbcX7btmWjW.." width="1400" height="1368" role="presentation"/></noscript>

Adding Login component to router

Then, if you change your browser url to localhost:8080/#/login you should see the new Logincomponent that we just created displayed in your browser:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*La8sG2AF2TezKeHZ.." width="1400" height="660" role="presentation"/></noscript>

Login screen

You will notice that the default menu is still there despite the fact that we didn’t put it in the html template of the Logincomponent? Well, if you open the App.vue file, the template of the App component is as follow:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2208/0*epMruqS91hVUNt47.." width="1104" height="666" role="presentation"/></noscript>

App component

The App component is the main component of the app and will be the first to be rendered. It contains a div with two router-link elements and a html component called router-view.

We will soon talk about the router-link element, but first, let’s see what is the router-view element.

Router-view is a component of vue-router:

The <router-view> component is a functional component that renders the matched component for the given path. Components rendered in <router-view> can also contain its own <router-view>, which will render components for nested paths.from vue-router documentation [https://router.vuejs.org/en/api/router-view.html](https://router.vuejs.org/en/api/router-view.html)</span>

So, when reaching [http://localhost:8080/#/login](http://localhost:8080/#/login) vue-router will render the attached component of the path/login we defined in src/router.js inside the router-view component. And since the App component also contain the nav div with the two router-link elements in his template, we also have them display in our view.

To avoid confusion with the navigation of the app we are creating, let’s remove this nav div from the App component and replace it with the vue logo. We already have the Vue logo inside the src/assets/ directory, so let’s use it!

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2144/0*8-6a0ioFUZP30NL2.." width="1072" height="558" role="presentation"/></noscript>

App component after removing nav div

Also, Since we are not going to use the About view, we can remove the file from our directory (src/views/About.vue) and also remove i t from our routes configuration in src/router.js

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1808/0*i_z9HkXmpoNl2o4v.." width="904" height="1134" role="presentation"/></noscript>

src/router/index.js

Now, let’s get back to our Login view add some style to our Login component.Inside the <style> element of your Login.vue file, add those styles.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*3R-rV9heyE5-Vrr3.." width="1400" height="1050" role="presentation"/></noscript>

CSS for Login component

After adding this style, you will notice the changes below:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*o28-urKDHuRDWdGP.." width="1400" height="738" role="presentation"/></noscript>

New style

The Sign Up View

The same way we created the Login view, we are going to create the Sign Up view. For that, create a new vue component called SignUp under src/views/.

As for the Login component, the SignUp component will consist, for now, of a simple form and some style attached to it.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*0NI6SbsZWFOCyjkx.." width="1400" height="1676" role="presentation"/></noscript>

Sign up component

Then, add the new component in our routes inside src/router.js

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*Q90i3uVtQDIEpm70.." width="1400" height="1270" role="presentation"/></noscript>

src/router/index.js

Then, if you open your browser to [http://localhost:8080/#/sign-up](http://localhost:8080/#/sign-up%60), you should have the following view:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*AMKtNGtuEN3Te6_A.." width="1400" height="738" role="presentation"/></noscript>

Sign up View

Navigation between views

If we look back to the schema of the app architecture we defined, we can navigate from the Login view to the Signup view, and from those two views to the Home view. How to do so?

Well, we will use another component of vue-routerthat we quickly saw before,called router-link.

<router-link> is the component for enabling user navigation in a router-enabled app. The target location is specified with the to prop. It renders as an <a> tag with correct href by default, but can be configured with the tag prop. In addition, the link automatically gets an active CSS class when the target route is active.from vue-router documentation: [https://router.vuejs.org/en/api/router-link.html](https://router.vuejs.org/en/api/router-link.html)</span>

So, in the Login and SignUp component, let’s implement router-link so we can navigate between those two views.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*mrTWoneio4aZ8Y9m.." width="1400" height="487" role="presentation"/></noscript>

src/view/login

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*3SIu7b_kYJ4faZeE.." width="1400" height="603" role="presentation"/></noscript>

src/view/signup

Now, you should be able to navigate between the two pages by using the links we just created.

The last part of navigation will consist to go from Login/SignUp views to the Home view. For now, since we don’t have any code implemented, we will do a simple redirection to the Home view when clicking on the Connection button, without any authentication checking.

With router-link, the navigation take places in the html part of the component, but now, we want to navigate between routes programmatically. To do so, we need to attach an event when clicking on the Connection button, and with Vue, we can do that with the v-on directive or with the @ alias for v-on directive.

The event we want to listen to is click. So, on the click event of the Connection button, we want to navigate to the Hello view.

To navigate programmatically between views, vue-router has a set of function we can use in our app. To know more about those functions, you take a look in their documentation https://router.vuejs.org/en/essentials/navigation.html.

In our example, we are going to use the replace function, because once the user is logged in, we want the Hello view as our starting route.

Let’s change our Login component to put this in place.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*UpJq6IL6We_G_fp7.." width="1400" height="1400" role="presentation"/></noscript>

src/views/login.vue

You can see inside the login function that we have this.$router.replace('home')

Why do we access the router with this? If you take a look into the main.js file, you’ll see that the router object is injected to the Vue app. That way, we can easily access it in every components of the app.

Also, we change the navigation to home, but we don’t have any hello path yet.

The default path of the Home component was / on the app initialization, but now that we know that the Home view will be only accessible when user is authenticated, let’s change the route so that the Home view is accessible when reaching /home path.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*iXQ33DDpV_BS8x2L.." width="1400" height="1270" role="presentation"/></noscript>

src/router/index.js

Now, back to our Login view, if you click on the Connection button, you’ll be redirect to the Home view ! You’ll see two Vue logo display. That’s normal ! Check the content of the Hello-world component in src/components/HelloWorld.vue ;). Remove the image from the template of the Hello-world component to avoid duplication of the Vue logo.

Firebase Integration

Now that we have our front-end app ready, let’s implement Firebase so we can use it’s authentication system !

3.1 Create a new project on Firebase

To use Firebase, you first need to create a new project on the firebase console. If you don’t have any account created, create one, then go to console.firebase.google.com.

Click on Add project . Them you should have a popup to create a new project. Choose the name you want. I choose to call it vue-firebase-tutorial,

Follow the prompts and finish the other steps until you reach your dashboard

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1500/1*fLZfalbbGRkHEM4Q.." width="750" height="585" role="presentation"/></noscript>

Firebase dashboard

Congrats ! Your Firebase project is created. Now, to integrate it in our app, click on the code icon above Add an app to get started.

Setup you app nickname and register the app.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1262/1*hGWQC-MSsHrYhXUB.." width="631" height="483" role="presentation"/></noscript>

Setting up the app

A popup with a code snippet should appear. Copy the code inside the second script balise. It should look like:

// Initialize Firebaselet config = {
  apiKey: "YOUR_API_KEY",
  authDomain: "YOUR_PROJECT_ID.firebaseapp.com",
  databaseURL: "https://YOUR_PROJECT_ID.firebaseio.com",
  projectId: "YOUR_PROJECT_ID",
  storageBucket: "YOUR_PROJECT_ID.appspot.com",
  messagingSenderId: "YOUR_MESSAGING_SEND_ID"
};firebase.initializeApp(config);</span>

Now, let’s back to our vue project. We need to add the Firebase module to our project. To do so:

$ npm install ——save firebase</span>

Once the installation is done, let’s import Firebase module to our app. Open the main.js file, and initialize Firebase with the configuration code we copied earlier.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*4OWL7wb2o-Ou27kt.." width="1400" height="1100" role="presentation"/></noscript>

main.js file

For the simplicity of the tutorial, we put the Firebase configuration in main.js file, but on real production system, avoid to do that and put it in a specific configuration file. Also, you may see appear in the console some Firebase warnings about only importing the part of the SDK we actually use. In production, you should definitely do that! But again, to keep the simplicity of this tutorial, I skip this part.

We have everything ready now to create new users on Firebase !

3.2 Create User on Firebase with the SignUp component

Let’s go back to our SignUp component and implement what we need to create users on Firebase.

To create a new user, we will need to get back the email and the password typed in our form inside our component controller. To do so, we are going to use the v-model directive of Vue.

You can use the v-model directive to create two-way data bindings on form input and textarea elements. It automatically picks the correct way to update the element based on the input type. Although a bit magical, v-model is essentially syntax sugar for updating data on user input events, plus special care for some edge cases.from Vue 2 documentation: [https://vuejs.org/v2/guide/forms.html](https://vuejs.org/v2/guide/forms.html)</span>

Once we retrieved the email and the password of the new user we want to create, we are going to use the Firebase function called createUserWithEmailAndPassword.

This Firebase function does exactly what the name says, it create a new user with an email and a password. You can know more about this function in the official Firebase documentation here: https://firebase.google.com/docs/reference/js/firebase.auth.Auth#createUserWithEmailAndPassword

Let’s add all that in our SignUp component:

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*uYsy_Gdenc1WBO87.." width="1400" height="1400" role="presentation"/></noscript>

signup.vue

The createUserWithEmailAndPassword function return a Firebase promise, with an onResolve and onReject callback. You can know more about the different type of Firebase promises here: (https://firebase.google.com/docs/reference/js/firebase.Promise).

For the moment, we just display an alert to see the result of the function.

Let’s try to create a new user in the interface.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*vbPW0U9FNPNngdmY.." width="1400" height="741" role="presentation"/></noscript>

It’s not working ! Why ?

The error message says:

_The given sign-in provider is disabled for this Firebase project. Enable it in the Firebase console, under the sign-in method tab of the Auth section._</span>

To have the possibility to create new user, we should enable the sign-in provider of Firebase. Let’s go back to the Firebase console, on the project we created earlier

On the Authentication part, we have a tab named SIGN-IN METHOD

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1734/1*T04iHbprq4yvikcE.." width="867" height="701" role="presentation"/></noscript>

You just need to enable the Email/Password provider. Then let’s retry creating a new user again

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/1926/1*39SThSqVfY3wLo4g.." width="963" height="317" role="presentation"/></noscript>

N/B: Trying to add a user from the signup page returns an error that says Email address is badly formatted

To add a user for now, navigate to the users section on your firebase dashboard and add a new email and password.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2056/1*-9OLthiY3-uM_XHu.." width="1028" height="409" role="presentation"/></noscript>

Adding a new user

Login with the new user

Now that we have a new user created, let’s try to login with this user ! (When you successfully create a new user on Firebase, it automatically sign in the user in to the application, but for this example, we are going to sign in again from the Login view)

Let’s go back to our Login component. We need to get back the email and the password of the user who try to login, and sign in this user into Firebase. This component will look like the SignUp component, but the change will be the function we will call. To sign in a user in Firebase, we are going to use the signInWithEmailAndPassword function provided by Firebase. It takes the email and password as parameters and return a Firebase promise.

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/2800/0*cGPOuCIkgsGSO8VG.." width="1400" height="1400" role="presentation"/></noscript>

login.vue

Now, let’s try to login with the user we just created

<noscript><img class="cp t u ho ak" src="miro.medium.com/max/5112/1*otr61G3AtTaken2x.." width="2556" height="1354" role="presentation"/></noscript>

It’s working ! Your user is now authenticated in Firebase.

Am working on updating this project and fixing the error we encountered earlier. Please if you have the solution, I’ll appreciate a comment.

You can follow me on Twitter or Instagram to get update on other articles and tutorials.

The source code of this project is available on Github.