[Modern Web Development Tutorial ] - Part 2 - Creating a front end with JWT auth using Quasar framework

in #utopian-io7 years ago (edited)

Repository

https://github.com/quasarframework/quasar
https://github.com/vuejs/vue
https://github.com/vuejs/vuex
https://github.com/feathersjs/feathers

What Will I Learn?

In this tutorial, we will be learning about

  • Quasar Framework
  • How to install and use Quasar
  • Building a JWT based authentication system with Quasar and Feathers.js

Requirements

In order to be fully able to grasp the contents of this tutorial, the audience must have knowledge of

Before you dive into this, you might want to follow the links above to related find relevant tutorials.

Difficulty

  • Intermediate

Tutorial Contents

In the previous post in this tutorial series, we learned how to create an API with pre configured JWT based authentication. We also tested our API using Postman and were able to authenticate our users with API calls. In this tutorial, we are going to create a front end that will communicate with the API we created and authenticate a user with us. For this we will be using the Quasar framework, a new but popular kid in the town but a lot of features, which is built on top of Vue.js.

What is Quasar framework? Why do we need it ?

The Quasar Website describes Quasar as a framework that can

Build responsive websites, PWAs, hybrid mobile Apps (that look native!) and Electron apps, all simultaneously using same codebase, powered with Vue.

Having quoted that, we can say that Quasar is our ultimate tool to create front ends for various platforms with a single code base. It can be thought as an alternative to react native. It is built on top of Vue.Js, another component based front end library which is easier to learn than React or Angular.

Quasar is recommended for applications that target multiple targets simultaneously and want to give a seamless browsing experience, irrespective of the device they are using. It can generate releases for any of the different platforms with a single command.

Getting started with Quasar

You can use Quasar in your application in three different ways

  • Standalone (embed into an existing project through CDN)
  • Quasar CLI
  • Vue CLI 3 Plug In

You can use any of the suitable methods but for the sake of simplicity, we will start with the Quasar CLI. To install Quasar CLI, navigate to your terminal( Or CMD in windows) and type :

npm install -g vue-cli

npm install -g quasar-cli

This will install the Vue-CLI and Quasar-CLI globally in your machine. now we can use the Quasar cli commands to quickly bootstrap our front end by simply typing

quasar init quasar-front-end

Follow the instructions and choose the required plug in when prompted as shown in below picture
Screenshot from 2018-06-17 18-33-05.png

It will create a new directory named quasar-front-end in the same folder where you ran the command. Lets open this directory in a code editor and see What Quasar generated for us with the above command.
Screenshot from 2018-06-17 18-44-57.png

As you can see Quasar has generated some files and folders for us which will help us write and organize our code.

The important file to note here is quasar.config.js file which is used to define and configure

  • Quasar components, directives and plugins that you’ll be using in your website/app.
  • Default Quasar I18n language pack
  • Icon pack(s) that you wish to use
  • Default icon set for Quasar components
  • Development server port, HTTPS mode, hostname and so on
  • CSS animations that you wish to use
  • App Plugins list (that determines order of execution too) – which are files in /src/plugins that tell ----- how your app is initialized before mounting the root Vue component
  • Global CSS/Stylus/… files to be included in the bundle
  • PWA manifest and Workbox options
  • Electron Packager and/or Electron Builder
  • IE11+ support
  • Extend Webpack config Object - Source

The Other important thing to note is the src/ directory, where our application logic will be created in form of vue and javascript files. It has different directories to store different modules, hence making the code well organised and modular.

Now to run the app, we can run

quasar dev

Which will start the development server on http://localhost:8080 in SPA mode, which is the default mode we will be using, although you can develop different versions as well by running following commands

# run development server (with default theme)
 quasar dev

# run development server with specific theme
  quasar dev -t mat
 quasar dev -t ios

# on specific port
  quasar dev -p 9090

# PWA
 quasar dev -m pwa

# Mobile App
 quasar dev -m cordova -T [android|ios] -t [mat|ios]

# Electron App
  quasar dev -m electron
# with iOS theme...
  quasar dev -m electron -t ios

When we navigate to the localhost:8080 in a browser, we can see the Quasar start app template, Which means we are ready to customize this app to build our own functionality.
Screenshot from 2018-06-17 18-55-36.png

So now, let's get started and edit the index.js file in default.vue directory to remove the starter template code.

Creating the application routes

By default, the quasar framework generates a routes.js file for us in the /src/routes folder, which will contain all the application routing logic for front end. There is only one route defined in the beginning for index route (/) as shown below.

// src/routes/routes.js

export default [
  {
    path: '/',
    component: () => import('layouts/default'),
    children: [
      { path: '', component: () => import('pages/index') }
    ]
  },

  { // Always leave this as last one
    path: '*',
    component: () => import('pages/404')
  }
]

Notice that the index route is having a child index route as well. We can now create our own routes for login, sign up and a secured home page by adding the following lines to src/routes/routes.js.

// src/routes/routes.js


export default [
  {
    path: '/',
    component: () => import('layouts/default'),
    children: [
      {
        path: '',
        component: () => import('pages/index')
      },
      {
        path: '/login',
        component: () => import('pages/Login')
      },
      {
        path: '/register',
        component: () => import('pages/Register')
      },
      {
        path: '/secured',
        component: () => import('pages/Secured')
      }
    ]
  },
  { // Always leave this as last one
    path: '*',
    component: () => import('pages/404')
  }
]

Since we have provided components Login, Register and Secured in our routes, we need to create them in the pages directory. You can use quasar new command that ships with the framework to quickly generate pages, components etc.

quasar new page Login
quasar new page Register
quasar new page Secured

This will generate three new vue files in the pages directory.
Screenshot from 2018-06-18 22-25-26.png

Now let us quickly edit the files to create the required forms.

// src/pages/Login.vue

<template>
  <q-page padding class="">
    <q-card >
  <q-card-title>
    Already a user? Log In To SwapSteem!
  </q-card-title>
  <q-card-separator />
  <q-card-main>
      <q-field
        icon="mail"
        label="Email"
        label-width= 3
        @blur="$v.form.email.$touch"
        :error="$v.form.email.$error"
        helper="Enter your registered email address to Log in"
        error-label="Please type a valid email address"
        >
        <q-input
        type="email"
        v-model="form.email"
        />
      </q-field>
      <q-field
        icon="vpn_key"
        label="Password"
        label-width= 3
        helper="Enter your password"
        :error="$v.form.email.$error"
        error-label="Please type a valid password"
        >
        <q-input
        type="password"
        v-model="form.password"
        />
      </q-field>
  </q-card-main>
  <q-card-separator />
  <q-card-actions align="center">
    <q-btn color="primary" align="center" label="Log In" @click="submit" />
  </q-card-actions>
</q-card>
</q-page>
</template>

<script>
import { required, email } from 'vuelidate/lib/validators'

export default {
  data () {
    return {
      form: {
        email: '',
        password: ''
      }
    }
  },
  validations: {
    form: {
      email: { required, email },
      password: { required }
    }
  },
  methods: {
    submit () {
      this.$v.form.$touch()

      if (this.$v.form.$error) {
        this.$q.notify('Please review fields again.')
      }
      this.$store.dispatch('user/login', {
        email: this.form.email,
        password: this.form.password,
        strategy: 'local'
      }).then(() => {
        this.$router.push('/secured')
      })
    }
  }
}
</script>

<style>
</style>

The above vue file defines a vue component with a Login form. it has two textfields for email and password, and a sign in button. The form is validated via the 'vuelidate' plugin from vue.js which checks the email string to be a valid email address and prevents user from submitting the form if there are any errors. On click of the Log In button, we are sending a 'vuex action' that will query our API for the email and password and return a JWT if the user exists and the password is valid.
In order to use 'vuex' we need to create a store. Please note that vue router and vuex are pre installed in our application because we chose them while bootstrapping our app, if you remember. To create a store again we can use the quasar new command as

quasar new store user

This will create a 'Vuex' store for user and also generate related files that we will need like actions, mutations etc. To create the login action, edit the 'src/store/user/actions.js'

// src/store/user/actions.js

/*
export const someAction = (state) => {}
 */
import { axiosInstance } from 'plugins/axios'
import { LocalStorage } from 'quasar'
export const login = (commit, creds) => {
  axiosInstance.post('/authentication', creds).then(res => {
    console.log(res.data.accessToken)
    LocalStorage.set('token', res.data.accessToken)
  })
}

The above code uses 'axios' to send an authentication request to our API with form data and upon success, takes the JWT from response and saves it in Localstorage.

Lastly we need to set this access token in the app state, in order to be used in any component. Edit the 'src/store/user/state.js' as


export default {
  token: localStorage.getItem('token') || ' '
}

To keep this tutorial short and user friendly, we will be covering the registration flow in the next tutorial. Till then we will put some placeholder text in Register and Secured pages like below.

  • Register.vue
// src/pages/Register.vue

<template>
  <q-page padding>
    <h1>This is Register Page!! Coming Soon!</h1>
  </q-page>
</template>

<script>
export default {
   name: 'Register',
}
</script>

<style>
</style>
  • Secured.vue
// src/pages/Secured.vue

<template>
  <q-page padding>
    <h1>This is secured Page!! You are authenticated!</h1>
  </q-page>
</template>

<script>
export default {
  name: 'Secured',
}
</script>

<style>
</style>
// src/pages/index.vue

<template>
  <q-page class="">
     <h1>This is Landing Page!! You are NOT authenticated!</h1>
     <router-link class="absolute-center" to="/login">Login</router-link>
  </q-page>
</template>

<style>
</style>

<script>
export default {
  name: 'PageIndex'
}
</script>

And that's it. We are all set, let us test our login flow by vising the browser at http://localhost:8080/
Screenshot from 2018-06-18 23-26-37.png

Click on Login Link to go to login page
Screenshot from 2018-06-18 23-27-13.png

Enter the user details you created in the previous tutorial to log in. On successful login, you should see the secured page.
Screenshot from 2018-06-18 23-27-48.png

Due to the length of the post, we will be covering authentication error handling and registration in the next tutorial. Till then,keep learning!

Curriculum

This is part 2 of my ongoing series - Modern web development

Proof of Work Done

The code generated in this tutorial while learning can be found on Github
Github Account : https://github.com/AneilPatel05

Sort:  

Nice post...resteemed. i will appreciate it if you FOLLOW ME back.

Resteeming random posts won't work on Steem @richybamz
This is considered spam!

Congratulations @aneilpatel! You have completed some achievement on Steemit and have been rewarded with new badge(s) :

Award for the number of upvotes received

Click on the badge to view your Board of Honor.
If you no longer want to receive notifications, reply to this comment with the word STOP

Do not miss the last post from @steemitboard!


Participate in the SteemitBoard World Cup Contest!
Collect World Cup badges and win free SBD
Support the Gold Sponsors of the contest: @good-karma and @lukestokes


Do you like SteemitBoard's project? Then Vote for its witness and get one more award!

Thank you for your contribution.
Some feedback to you:

  • Are you in any way affiliated with SwapSteem? as i noticed you used their name in your sample code.
  • Your tutorial is basically replicating the official documentation of quasar setup, we would normally urge to bring more added value to the community.
  • While you did reference the official documentation in the definition of quasar, yet you failed to do so in other sections where you had copied content exactly as is, particularly from here, this is considered plagiarism.

Unfortunately this will entice a temporary ban for 15 days. Please make sure to avoid such occurrences in the future to avoid a permanent ban.

Edit: as this was a confirmed unintentional mistake by author, ban has been cancelled.


Need help? Write a ticket on https://support.utopian.io/.
Chat with us on Discord.
[utopian-moderator]

Congratulations @aneilpatel! You have completed some achievement on Steemit and have been rewarded with new badge(s) :

Award for the total payout received

Click on the badge to view your Board of Honor.
If you no longer want to receive notifications, reply to this comment with the word STOP

Do not miss the last post from @steemitboard!


Participate in the SteemitBoard World Cup Contest!
Collect World Cup badges and win free SBD
Support the Gold Sponsors of the contest: @good-karma and @lukestokes


Do you like SteemitBoard's project? Then Vote for its witness and get one more award!

Coin Marketplace

STEEM 0.13
TRX 0.34
JST 0.035
BTC 108074.45
ETH 4399.12
USDT 1.00
SBD 0.83