Setting up JWT Authentication in Typescript with Express, MongoDB, Babel, Prettier, ESLint, and Husky: Part 2
- Mohammad Abu Mattar
- Backend
- 03 Jul, 2022
- 19 Mins read
Introduction
Why do we even need an authentication mechanism in an application? in my opinion, it doesn’t need to be explained. The phrases authentication and authorization have likely crossed your lips, but I must emphasize that they have two distinct meanings.
- Authentication: Any security approach must start with authentication, verifying that users are who they claim to be.
- Authorization: Authorization in the context of system security describes the procedure for authorizing user access to a certain resource or function. The words “access control” and “client privilege” are commonly used interchangeably.
At the same time, the words “authentication” and “authorization” are used in the context of network security. In this context, authentication is the process of verifying that a user is who they claim to be. Authorization is the process of verifying that a user has the necessary rights to access a certain resource or function.
We will learn how to create an authentication system using JWT in this tutorial. We will also learn how to create an authorization system using JWT with Typescript, Express. and the tutorial is a continuation of the previous tutorial.
Directory and File Structure
We’ll start by creating a directory structure for our application, and then we’ll create a file structure for our application.
Don’t be overwhelmed; this structure will be helpful after the program is finished and you start expanding the file structure for the business logic. This is just my opinion; perhaps you’ll organize the directory and files differently.
We’ll be continuing build-up in the last tutorial repository.
To better arrange the file structure and identify the key files, certain adjustments will be made to tsconfig.json
.
tsconfig.json
nevertheless, in order to use the file structure, we must install a package called module-alias
. To install the package, use the following command after generating the project:
and we need to do some change to package.json
and add _moduleAliases
:
Environment Variables
A basic text configuration file called a .env
file or dotenv
file is used to manage the environment constants for your applications. The vast bulk of your application will remain the same throughout the Local, Staging, and Production environments. However, there are times when some configurations need to be changed between environments in various applications. Typical setup adjustments across contexts might be, but are not restricted to:
- URL’s and API keys
- Domain names
- Public and private authentication keys
- Service account names
An environment constant is a variable whose value is set outside to the application, generally via operating system capability. Any number of environment variables may be generated and made accessible for use at one time; each environment variable consists of a name/value pair.
After creating the directory structure, we’ll create a file called .env
and .env.example
in the root directory:
.env
: This file will contain the configuration for the application..env.example
: is the file that contains all of the configurations for constants that.env
has, but without values; only this one is versioned.env.example
serves as a template for building a.env
file that contains the information required to start the program.
Now we add a new variable to .env
:
.env
.env.example
They will now be loaded and used using the library dotenv
, and environment variables will be verified by a different library called envalid
.
variable.validation.ts
variable.env.ts
Setup logger for development
I had a problem setting up the logger when constructing a server-side application based on Node and Express router. Conditions for the answer:
- Logging application event
- Ability to specify multiple logs level
- Logging of HTTP requests
- Ability to write logs into a different source (console and file)
I found two possible solutions:
- Morgan: HTTP logging middleware for express. It provides the ability to log incoming requests by specifying the formatting of log instance based on different request related information.
- Winston: Multiple types of transports are supported by a lightweight yet effective logging library. Because I want to simultaneously log events into a file and a terminal, this practical feature is crucial for me.
I’ll use Winston for the logging, first I’ll install the package:
We’ll begin by introducing the constants, which will be applied as follows:
dateformat.constant.ts
path.constant.ts
We’ll now create the winston
as a function to make it simpler to use:
logger.util.ts
Setup MongoDB using Mongoose
What is MongoDB?
MongoDB is a NoSQL database is used to store structured data. It is a document-oriented database made to operate with documents that resemble JSON.
What is Mongoose?
Mongoose is a MongoDB object modeling library. It is a MongoDB driver for Node.js.
first I’ll install the package:
We’ll begin setting up the mongoose
to connect to the database right away:
db.config.ts
after that, we’ll do some changes to index.ts
, which is the entry point of the application:
index.ts
We will now begin to construct the user schema, but before we do, we must include constants for numbers:
number.constant.ts
user.schema.ts
Now, we must create a model in order to interact with this schema:
model.constant.ts
user.interface.ts
user.model.ts
In my opinion, I build a file to handle all queries in the database through a specific cluster.
user.repository.ts
Setup Validation using Joi
What is Joi?
Joi is a library that helps you validate data. It is a great tool to validate data before you save it to the database.
first I’ll install the package:
regex.constant.ts
user.validation.ts
Setup JWT Authentication
What is JWT?
JWT is a JSON Web Token. It is a standard for representing claims to be transferred between parties in a secure way.
Alternatively explanation as a book’s:
An open industry standard called JSON Web Token is used to exchange data between two entities, often a client (like the front end of your app) and a server (like the back end of your app). They include JSON objects that include the necessary information to be communicated. To ensure that the JSON contents, also known as JWT claims, cannot be changed by the client or an unintentional party, each JWT is additionally signed using cryptography (hashing).
we need to install two libraries:
jsonwebtoken
is a library that helps you create, sign, and verify JSON Web Tokens.crypto-js
is a library that helps you encrypt and decrypt data.
we need to install the types for the library:
to encrypt, decode, and produce an access token, create a file:
user.security.ts
message.constant.ts
using the user validation form joi as input, construct middleware:
validation.middleware.ts
We’ll now link the repository, security, and a service for authentication:
auth.service.ts
api.constant.ts
auth.controller.ts
We will now develop a validation for each JWT that we receive:
token.validation.ts
Before moving on, we must make a few adjustments to the configuration file and type in the typescript request:
index.d.ts
tsconfig.json
message.constant.ts
After that, we can develop middleware to check if the request has authorization for the same end point:
authenticated.middleware.ts
We’ll now link the repository, security, and service for user:
user.service.ts
api.constant.ts
message.constant.ts
To access the service for what we need to build the methods, we’ll make a new contact with the middleware for each authorized user and input validation:
user.controller.ts
api.constant.ts
after that, we’ll do some changes to the www.ts
file:
www.ts
Summary
All in all, you learnt about JWTs and how to develop a router-level middleware for JWT authentication in Node.js and Express.js using TypeScript. If we wanted to authenticate all incoming requests to our API, we could also utilize it as an application-level middleware.
All code from this tutorial as a complete package is available in this repository. If you find this tutorial helpful, please share it with your friends and colleagues, and make sure to star the repository.