Adventures with NestJS: Building an API. Part 1

franciscomessina

Fran Messina

Posted on August 22, 2022

Adventures with NestJS: Building an API. Part 1

This is not exactly going to be a tutorial, since I am not sure I know enough to be teaching people, but I wanted to try to document my process of building an app, and thought that writing some articles about it might help me and hopefully maybe help some people who read them. I won't be explaining every thing in extreme detail, in case you don't understand something or think I missed something important please let me know, however I highly recommend reading the Nest documentation since in most cases it has everything very clearly explained. Another great resource I used when learning nest was a series of blog posts by Marcin Wanago: API with nestjs

The final app probably will evolve with time but some things it will include are:

  • Authentication & Authorization
  • Products with Variants and different stock locations(warehouses, stores)
  • Integration with MercadoLibre (A massive online marketplace from Argentina)
  • Payments with MercadoPago.

The app will be a all in one management system and online store for a used books store, since I work at one and having something like it would make my daily job a lot easier. The main technologies I will be using are:

  • NestJs
  • PostgreSQL
  • Redis
  • Typescript
  • GraphQL

Somewhere along the way I will also build the Admin Frontend.

In this article we will get started by setting up the project:

First let's create a new nest app:

nest new {app_name}

if you don't have the nest CLI installed you can install it with:

npm i -g @nestjs/cli

it is the easiest way to start nest applications since it has a lot of generators to reduce the time you spend writing boilerplate code. The nest CLI will ask you what package manager you want to use, I will chose yarn.

Now let's add the first packages we are going to use:

yarn add @nestjs/config @nestjs/graphql @nestjs/apollo @nestjs/typeorm apollo-server-express graphql typeorm pg
Enter fullscreen mode Exit fullscreen mode

In order to setup GraphQl and TypeORM we have to add the following to our app.module.ts file:

@Module({
  imports: [
    ConfigModule.forRoot({
      isGlobal: true,
    }),
    TypeOrmModule.forRootAsync({
      inject: [ConfigService],
      useFactory: (configService: ConfigService) => ({
        url: configService.get('POSTGRES_URL'),
        // here we will need to add every entity we create
        entities: [],
        type: 'postgres',
        synchronize: true,
      }),
    }),
    GraphQLModule.forRootAsync<ApolloDriverConfig>({
      driver: ApolloDriver,
      inject: [ConfigService],
      useFactory: (configService: ConfigService) => ({
        playground: true,
        debug: true,
        autoSchemaFile: path.join(process.cwd(), 'src/graphql/schema.gql'),
      }),
    }),
  ],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}
Enter fullscreen mode Exit fullscreen mode

The first module we are importing is the ConfigModule in order to be able to get information from .env files, and we are making it global so we don't have to import it in any other module. Then we setup TypeOrmModule in order to be able to use postgresql, syncronize: true means TypeOrm will try to keep our DB schemas up to date with the entities we define, this is not recommended in production, where you should use migrations.

For GraphQL we are going to use the Code First approach, that's why we have the autoSchemaFile option in the module config. This will make nest scan our code for classes and their properties decorated with the GraphQL decorators and automatically generate the schema.

Before we start our app we have to setup a Postgres Db, for this I am going to use Docker Compose, let's create a docker-compose.yml file in the project root directory. And add the following inside:

version: '3'

services:
  postgres:
    image: postgres:14
    container_name: postgres_db
    restart: unless-stopped
    volumes:
      - ./postgres:/var/lib/postgresql/data
    ports:
      - "5432:5432"
    environment:
      POSTGRES_DB: postgres
      POSTGRES_PASSWORD: postgres
Enter fullscreen mode Exit fullscreen mode

If you know how to use docker compose then it is one of the easiest ways to setup a database for development, if not you can always install postgres in your computer.

Let's create our first resolver running:

nest g resolver app --flat

and inside add:

import { Resolver, Query } from '@nestjs/graphql';

@Resolver()
export class AppResolver {
  @Query(() => String)
  hello() {
    return 'hello world';
  }
}
Enter fullscreen mode Exit fullscreen mode

With all of this done we should we able to run yarn start:dev and go to localhost:3000/graphql to the graphql playground, and in there run our hello query.

Graphql Playground

You can browse the code in this repository: nest-adventures

This is it for now, in the next post we will be adding our products and related functionalities.

Thank you for reading. This is the first post I ever wrote so any comments about how to improve or if you liked will be highly appreciated.

💖 💪 🙅 🚩
franciscomessina
Fran Messina

Posted on August 22, 2022

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related