Photo by Nangialai Stoman on Unsplash
TypeScript CRUD Rest API: Building a Robust Application with Nest.js, TypeORM, Postgres, Docker, and Docker Compose
Building a Robust TypeScript CRUD Rest API with Nest.js, TypeORM, Postgres, Docker, and Docker Compose
As the development world evolves, the need for reliable and scalable applications grows. Today, building robust applications requires an understanding of multiple programming languages and technologies. TypeScript is one such language that has gained popularity in recent years due to its type-safe features, which enable developers to write code with fewer errors. In this article, we will dive into how to build a TypeScript CRUD Rest API using Nest.js, TypeORM, Postgres, Docker, and Docker Compose.
Introduction to TypeScript
TypeScript is a strongly typed superset of JavaScript that compiles to plain JavaScript. It was developed by Microsoft and has gained popularity due to its ability to catch errors at compile time, resulting in fewer errors at runtime. TypeScript is compatible with any JavaScript library or framework, making it easy to integrate into existing projects.
What is Nest.js?
Nest.js is a popular framework for building scalable Node.js applications. It uses modern JavaScript features and incorporates ideas from other frameworks such as Angular, Express, and React. Nest.js is built on top of the Express framework, making it easy to integrate existing Express middleware. It also comes with built-in support for WebSocket servers and GraphQL.
TypeORM and its Benefits
TypeORM is an Object-Relational Mapping (ORM) library that allows developers to interact with databases using TypeScript or JavaScript. It supports a variety of databases such as MySQL, PostgreSQL, MongoDB, and more. With TypeORM, developers can write queries using TypeScript or JavaScript, making it easier to manage database interactions. It also allows for the creation of database schemas using TypeScript classes.
PostgreSQL Database
PostgreSQL is a powerful open-source relational database management system. It supports complex queries, transactions, and concurrency control. It is widely used in web applications due to its reliability and scalability.
Docker and Docker Compose
Docker is a popular platform for developing, shipping, and running applications in containers. Containers are lightweight and can be easily moved from one environment to another. Docker Compose is a tool for defining and running multi-container Docker applications. It simplifies the process of running multiple containers by defining them in a single file.
Creating the Project
The first step in building a TypeScript CRUD Rest API is to create the project. We will use the Nest.js CLI to create the project structure.
Step 1: Installing Nest.js CLI
To install Nest.js CLI, open the terminal and run the following command:
npm i -g @nestjs/cli
Step 2: Creating the Project
Once the Nest.js CLI is installed, run the following command to create the project:
nest new project-name
This command will create a new Nest.js project with the given name.
Step 3: Installing Dependencies
We will now install the required dependencies for our project. Run the following command in the terminal:
npm install --save @nestjs/typeorm typeorm pg
This command installs the required dependencies for Nest.js and TypeORM.
Setting up the Database
The next step is to set up the PostgreSQL database. We will use Docker and Docker Compose to create a PostgreSQL container.
Step 1: Creating a Docker Compose File
Create a file named docker-compose.yml
in the root directory of the project and paste the following code:
version: '3'
services:
db:
image: postgres
restart: always
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
ports:
- 5432:5432
This code defines a PostgreSQL container with a default username and password.
Step 2: Starting the Container
To start the PostgreSQL container, run the following command in the terminal:
docker-compose up -d
This command will start the PostgreSQL container in detached mode.
Step 3: Creating the Database
We will now create a database named nest_crud
in the PostgreSQL container. Run the following command in the terminal:
docker exec -it <container-id> psql -U postgres
Replace <container-id>
with the container ID of the PostgreSQL container. This command opens a psql shell.
Run the following command in the psql shell to create the nest_crud
database:
CREATE DATABASE nest_crud;
Step 4: Configuring TypeORM
The next step is to configure TypeORM to use the PostgreSQL database. Open the app.module.ts
file and add the following code:
typescriptCopy codeimport { Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { AppController } from './app.controller';
import { AppService } from './app.service';
import { ConfigModule } from '@nestjs/config';
@Module({
imports: [
ConfigModule.forRoot(),
TypeOrmModule.forRoot({
type: 'postgres',
host: 'localhost',
port: 5432,
username: 'postgres',
password: 'postgres',
database: 'nest_crud',
autoLoadEntities: true,
synchronize: true,
}),
],
controllers: [AppController],
providers: [AppService],
})
export class AppModule {}
This code imports the TypeOrmModule
and configures it to use the PostgreSQL database.
Creating the API
The next step is to create the API. We will create a basic CRUD API for managing products.
Step 1: Creating the Product Entity
Create a file named product.entity.ts
in the src
folder and add the following code:
import { Entity, Column, PrimaryGeneratedColumn } from 'typeorm';
@Entity()
export class Product {
@PrimaryGeneratedColumn()
id: number;
@Column()
name: string;
@Column()
description: string;
@Column()
price: number;
}
This code defines a Product
entity with the necessary columns.
Step 2: Creating the Product Service
Create a file named product.service.ts
in the src
folder and add the following code:
import { Injectable } from '@nestjs/common';
import { InjectRepository } from '@nestjs/typeorm';
import { Repository } from 'typeorm';
import { Product } from './product.entity';
@Injectable()
export class ProductService {
constructor(
@InjectRepository(Product)
private readonly productRepository: Repository<Product>,
) {}
async findAll(): Promise<Product[]> {
return this.productRepository.find();
}
async findOne(id: number): Promise<Product> {
return this.productRepository.findOne(id);
}
async create(product: Product): Promise<Product> {
return this.productRepository.save(product);
}
async update(id: number, product: Product): Promise<Product> {
await this.productRepository.update(id, product);
return this.productRepository.findOne(id);
}
async delete(id: number): Promise<void> {
await this.productRepository.delete(id);
}
}
This code defines a ProductService
with the necessary CRUD methods.
Step 3: Creating the Product Controller
Create a file named product.controller.ts
in the src
folder and add the following code:
import { Controller, Get, Post, Put, Delete, Body, Param } from '@nestjs
import { ProductService } from './product.service';
import { Product } from './product.entity';
@Controller('products')
export class ProductController {
constructor(private readonly productService: ProductService) {}
@Get()
async findAll(): Promise<Product[]> {
return this.productService.findAll();
}
@Get(':id')
async findOne(@Param('id') id: number): Promise<Product> {
return this.productService.findOne(id);
}
@Post()
async create(@Body() product: Product): Promise<Product> {
return this.productService.create(product);
}
@Put(':id')
async update(
@Param('id') id: number,
@Body() product: Product,
): Promise<Product> {
return this.productService.update(id, product);
}
@Delete(':id')
async delete(@Param('id') id: number): Promise<void> {
return this.productService.delete(id);
}
}
This code defines a ProductController
with the necessary CRUD endpoints.
Step 4: Creating the Nest Application
Create a file named main.ts
in the src
folder and add the following code:
typescript
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
await app.listen(3000);
}
bootstrap();
Step 5: Testing the API
To test the API, run the following command in the terminal:
npm run start
This command starts the Nest application.
Open Postman and create the following requests:
GET /products - Get all products
GET /products/{id} - Get a specific product
POST /products - Create a new product
PUT /products/{id} - Update an existing product
DELETE /products/{id} - Delete an existing product
Test the requests to ensure that the API is working correctly.
Conclusion
In this article, we have learned how to create a TypeScript CRUD REST API using Nest.js, TypeORM, PostgreSQL, Docker, and Docker Compose. We have covered how to set up the development environment, configure the database, and create the API. We have also learned how to test the API using Postman. With this knowledge, you can now create your own CRUD APIs using these technologies.