Building Full-Stack Applications Using Nest.js and Angular

In this article, we’ll see how we can use Nx (Nrwl Extensions) to create a full-stack application. The application will feature a frontend application built with Angular and a backend application that uses Nest.js.

Nrwl Extensions (Nx) is a project started by Google developers. It is an open-source project that provides a set of extensions (schematics and builders) to extend the functionality of the Angular . It provides commands for creating workspaces that contain multiple projects. Nrwl Extensions not only provides commands for managing complex and robust Angular projects but also for creating full-stack projects using Express and Nest.js
Before we get started, this article requires a basic understanding of Angular and Nest.js.

Initializing Application

Nrwl doesn’t replace the Angular CLI) — rather it extends the functionality of the CLI with commands to create multiple apps within a workspace. To get started working with Nrwl, you’ll have to install the Angular CLI first. Run the following command to install the CLI:


npm install -g @angular/cli

To use Nrwl, you have the options of installing it globally by running the following command:


npm install -g @nrwl/schematics

Or you could leverage the power of npx to create a workspace using the create-nx-workspace:


npx create-nx-workspace my-workspace

If you wish to integrate Nx into an existing Angular application, run the following command in a terminal within your project folder:


ng add @nrwl/schematics

To begin creating our project, we’ll create a workspace using the create-nx-workspace command. Run the following command to create a workspace called fullstack-angular.


create-nx-workspace fullstack-angular

This command will generate a workspace with no bootstrapped applications within. A workspace provides setup for listing using tslint, editor support for linting using tsconfig.json and prettier for code formatting.

It also provides a jest config file for quick testing. Jest is a testing framework by Facebook.

Next, we’ll see how we can create and serve a frontend application that runs on Angular using the CLI and Nx.

Creating the Frontend Application

Nx is a smart tool that supports a mono-repo development style. It provides a way to allow the projects within the workspace to interact with each other. With Nx you can manage different project types within the workspace, ranging from libraries to applications.

Nx provides a visualization tool that lets you see how the projects within your workspace are connected. You can access this tool by running the following command:


npm dep-graph

This is image title

The screenshot above shows how the projects in the workspace are connected. Next we’ll create the frontend application using the CLI.

Run the following command on a terminal within the project folder:


ng generate application my-store

After running this command, you’ll see different prompts. Let’s walk through each one:

? In which directory should the application be generated?

The first command asks where you’d like your application to be generated. It’s best to leave this blank so your application will be generated within the apps folder in the workspace.

? Would you like to add Angular routing? (y/N)

The next prompt is about routing. If you wish to create routes in your application, reply with y or you can skip this prompt.

PS: You can always add routing later on in your application.

? Which stylesheet format would you like to use? (Use arrowkeys)

❯ CSS

SCSS

SASS

LESS

Stylus

The next prompt is asking about your stylesheet of choice. If you prefer working with pre-processors, you can choose whichever you’re most comfortable with.

? Which Unit Test Runner would you like to use for the application? (Use arrow keys)

Karma

Jest

Here you have to choose the unit test runner you want to use with your application. Jest has been configured for the workspace already, so I’d recommend it. But you can still choose Karma if you’re more comfortable with it. It’s great to have options and Nx does well providing these options.

? Which E2E Test Runner would you like to use for the application? (Use arrow keys)

Cypress

Protractor

Then you have the e2e prompt. You can use either of them, whichever suits your application.

Finally, there’s the tags prompt, which you can leave blank. This prompt is asking for tags you wish to add that will be used for linting in your application:

? Which tags would you like to add to the application? (used for linting)

Again, you can leave this blank.

After the prompts, the command generates an Angular application within the apps folder, it also generates an e2e folder for running end-to-end testing for the application. You can start the application by running the command below:


    ng serve my-store

This should start your application on http://localhost:4200.

Nx provides a command to integrate state management into our application using @ngrx/store. Running the command below will generate actions, effects, and actionTypes for populating your store and a reducer for acting on the dispatched actions. To read more on using @ngrx/store, you can visit their official website and read through their robust documentation.

Run the following command to add state management to the my-store application:


ng generate ngrx todos --module=apps/my-store/src/app/app.module.ts

The command above tells the CLI to generate an ngrx store named todos in the my-store app module. If you check your apps/my-store/app folder, you should see a newly generated folder named +state. It contains files for actions, effects, selectors, and reducer. It also contains spec files to test them.

Creating the Backend Application

The backend application will be making use of Nest.js. According to the documentation:

Nest is a framework for building efficient, scalable Node.jsserver-side applications. It uses progressive JavaScript, is built with TypeScript (preserves compatibility with pure JavaScript), and combines elements of OOP Object Oriented Programming, FP (Functional Programming, and FRP (Functional Reactive Programming).

Nx offers two frameworks for creating backend applications: Express and Next.js. We’ll be going with Nest.js because of how similar it is to Angular and how it integrates seamlessly with Angular applications. It breeds familiarity because Nest.js uses similar techniques for development. They use modules, providers, and pipes just like Angular, and controllers in place of components.

With Nx, you can create a backend application that communicates seamlessly with the frontend application using the following command:


    ng generate node-app store-api --frontend-project=my-store

The command above creates a Node application called store-api and creates a proxy to the my-store Angular application. This makes it easy for the Angular application to communicate with the server.

By running this command, you’ll be faced with some prompts asking about your framework of choice, the unit testing framework, etc. The framework for this project is Nest.js, so ensure you select that option.

After the command has been run successfully, start the server by running the command below:


    ng serve store-api

Then you can visit http://localhost:3333/api. Your view should be similar to the screenshot below:

Making Requests

Let’s see how we can make requests to the backend application. Nx made this easier by creating a proxy to the backend. Within the my-store app, there’s a file proxy.conf.json, and within the file there’s the setup for proxying requests:


    {

    "/api": {

     "target": "http://localhost:3333",

     "secure": false

    }

    }

Which means, if we want to communicate with the backend, we’ll make requests to /api endpoint and it’ll proxy to [http://localhost:3333](http://localhost:3333).

Next, let’s update the Angular application to fetch items from the backend(store-api). Open the apps/my-store/src/app/app.component.ts file and update it to make a request to the server using the HttpClient:


    // apps/my-store/src/app/app.component.ts

    import { Component, OnInit } from '@angular/core';

    import { HttpClient } from '@angular/common/http'

    import { Observable } from 'rxjs';

    interface Product{

    name: String;

    price: Number;

    stock: Number

    }

    @Component({

    selector: 'fullstack-angular-root',

    templateUrl: './app.component.html',

    styleUrls: \['./app.component.css'\]

    })

    export class AppComponent {

    products: Observable<Product\[\]>;

    constructor(private http: HttpClient){

     this.products = this.http.get<Product\[\]>('/api/products');

    }

    }

Then we’ll update the view template to render the list of products. Open the apps/my-store/src/app/app.component.html file and copy the snippet below into the file:


    <section>

    <ul>

     <li \*ngFor="let product of products | async">

      Name: <span>{{product.name}}</span> <br/>

      Price: <span>{{product.price}}</span><br/>

      Stock: <span>{{product.stock}}</span>

      <hr>

     </li>

    </ul>

    </section>

Next, we’ll import the HttpClientModule into the project’s app.module.ts file. Open the file and include the HttpClientModule in the imports array.


    // apps/my-store/src/app/app.module.ts

    import { BrowserModule } from '@angular/platform-browser';

    import { NgModule } from '@angular/core';

    // ... others imports

    import { HttpClientModule } from '@angular/common/http';

    @NgModule({

    declarations: \[AppComponent\],

    imports: \[

     // ...other imports,

     HttpClientModule,

    \],

    providers: \[\],

    bootstrap: \[AppComponent\]

    })

    export class AppModule {}

Creating the Products Endpoint

In the Angular application, we’re making a request to the api/products endpoint. This route hasn’t been created in the node application. Let’s update the app controller to create a products route that returns a list of products.

Open the apps/store-api/src/app/app.controller.ts file and update it to be similar to the code below:


    // apps/store-api/src/app/app.controller.ts

    import { Controller, Get } from '@nestjs/common';

    import { AppService } from './app.service';

    @Controller()

    export class AppController {

    constructor(private readonly appService: AppService) {}

    @Get('products')

    getData() {

     return this.appService.getData();

    }

    }

Then update the service file (app.service.ts) to return the list of products:


    import { Injectable } from '@nestjs/common';

    interface Product{

    name: String;

    price: Number;

    stock: Number

    }

    @Injectable()

    export class AppService {

    private products: Product\[\] = \[

     {

      name: 'First product',

      price: 22.45,

      stock: 10

     },

     {

      name: 'Second product',

      price: 12.45,

      stock: 5

     }

    \]

     getData(): Product\[\] {

     return this.products;

    }

    }

Start the node backend by running the following command (ng serve store-api) and the frontend using ng serve my-store.

Navigate to http://localhost:4200 and you should see something similar to the screenshot below:

We’ve successfully set up a full-stack application with the help of Nrwl extensions. Nx is also useful for creating libraries — you can set up these libraries to communicate with your backend and frontend applications. You can also set up a library that can be easily published to npm. To learn more about creating libraries using Nx, visit their official documentation here.

Conclusion

In this article, we’ve seen how we can use Nx to create a full-stack application. The application will feature a frontend application built with Angular and a backend application that uses Nest.js. Nx provides extensions to the Angular CLI that help us manage workspaces that can feature multiple applications and libraries. These workspaces feature setup that supports linting using tslint and prettier for code formatting. Visit the project’s official documentation to read more about the project.

#angular #node-js #web-development

Building Full-Stack Applications Using Nest.js and Angular
152.25 GEEK