热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

为什么用nestjs_为什么你应该开始使用nestjs

为什么用nestjsNestJSisaframeworkforbuildingserversideNodeJSapp

为什么用nestjs

NestJS is a framework for building serverside NodeJS applications. NestJS comes with the philosophy of Angular application. When I say Angular like application that means loosely coupled, highly scalable architecture. NestJS adopted both TypeScript and Angular features. TypeScript makes it easy to define data types. TypeScript comes with both basic as well as advanced data types. We can also make complex use cases using TypeScript. Angular comes with features of Inheritance, advanced dependency injection, dynamic modules, and service. These Angular features help in creating large enterprise applications with scalability. NestJS uses both TypeScript and Angular features on the server-side.

NestJS是用于构建服务器端NodeJS应用程序的框架。 NestJS附带了Angular应用程序的理念。 当我说类似Angular的应用程序时,意味着松散耦合,高度可扩展的体系结构。 NestJS同时采用了TypeScript和Angular功能。 使用TypeScript可以轻松定义数据类型。 TypeScript包含基本数据类型和高级数据类型。 我们还可以使用TypeScript编写复杂的用例。 Angular具有继承,高级依赖项注入,动态模块和服务的功能。 这些Angular功能有助于创建具有可伸缩性的大型企业应用程序。 NestJS在服务器端同时使用TypeScript和Angular功能。

NodeJS和NestJS抽象的问题 (Problem with NodeJS and NestJS abstraction)

NodeJS comes with loads of libraries. Javascript makes frontend developer to easily create server-side Node application using express. However many frontend frameworks now using TypeScript which provides great leverage of type safety. So you ask what is the big deal we can use TypeScript in NodeJS server-side applications. Yes, we can use, however, NestJS allow next level abstraction. It provides all the features of TypeScript plus Angular features. So it is a great framework for Angular, Vue, and React developers.

NodeJS附带了许多库。 Javascript使前端开发人员可以使用express轻松创建服务器端Node应用程序。 但是,现在许多前端框架都使用TypeScript,它提供了类型安全性的强大杠杆作用。 因此,您问我们可以在NodeJS服务器端应用程序中使用TypeScript有什么大不了的事情。 是的,我们可以使用,但是,NestJS允许进行下一级抽象。 它提供TypeScript的所有功能以及Angular功能。 因此,对于Angular,Vue和React开发人员来说,这是一个很好的框架。

  • NestJS provides provide similar kind of architecture to other serverside applications i.e. .Net Core Web APIs and other Java rest APIs.

    NestJS提供了与其他服务器端应用程序(即.Net Core Web API和其他Java rest API)类似的架构。
  • NestJS provide features similar to Angular. So it is very easy for an Angular developer to switch on the server-side.

    NestJS提供的功能类似于Angular。 因此,Angular开发人员在服务器端切换非常容易。
  • The learning curve is not that steep. It is a very similar architecture for Angular, Java, and .Net developers.

    学习曲线并不那么陡峭。 对于Angular,Java和.Net开发人员来说,这是一个非常相似的体系结构。
  • Fully utilizes TypeScript features. Also uses Angular architectural prospect i.e. using interceptor, guards, injection, module, and services.

    充分利用TypeScript功能。 还使用Angular体系结构前景,即使用拦截器,防护,注入,模块和服务。
  • Uses TypeORM which gives leverage to connect with SQL and NoSQL databases.

    使用TypeORM,它可以利用它来连接SQL和NoSQL数据库。
  • Since NestJs is an Abstraction over the NodeJS. So we can use NodeJS libraries. This gives NestJS great leverage.

    由于NestJs是NodeJS的抽象。 因此,我们可以使用NodeJS库。 这使NestJS发挥了很大的作用。
从头开始创建NestJS产品API (Creating NestJS Product API from Scratch)

We will create here a CRUD API for using NestJS. Below is the GitHub link for more control over the project. You can fork it and play around it.

我们将在此处创建一个使用NestJS的CRUD API。 以下是GitHub链接,可更好地控制该项目。 您可以将其分叉并在其周围玩耍。

First, install NestJS globally and then create a new project. Check the below command and execute it.

首先,在全局安装NestJS,然后创建一个新项目。 检查以下命令并执行。

npm i -g @nestjs/cli
$ nest new nest-product-api

Now install dependencies and open the project in visual code.

现在安装依赖项,并以可视代码打开项目。

npm installcode .

Now create a product module. The project structure of NestJS is very similar to Angular. We can create modules, controllers in place of components, Services, interceptors, etc. Let's create a product module, controller, and services.

现在创建一个产品模块。 NestJS的项目结构与Angular非常相似。 我们可以创建模块,控制器来代替组件,服务,拦截器等。让我们创建产品模块,控制器和服务。

import { Module } from '@nestjs/common';
import { ProductsController } from './products.controller';
import { ProductsService } from './products.service';
@Module({
imports: [],
controllers: [ProductsController],
providers: [ProductsService],
})
export class ProductsModule {}

Now add the product module in the root module.

现在,将产品模块添加到根模块中。

@Module({imports: [ ProductsModule],controllers: [AppController],providers: [AppService],})export class AppModule {}

For the demo, we are building the Product API. The product has a product id, product name, product code, and product description. Now create Product data models and a class that implements it. In the class, the constructor accepts product properties and initialize the product.

对于演示,我们正在构建产品API。 该产品具有产品ID,产品名称,产品代码和产品说明。 现在创建Product数据模型和一个实现它的类。 在该类中,构造函数接受产品属性并初始化产品。

export class Product implements IProduct {constructor(public prodid: string,public productName: string,public productDesc: string,public prodAddedDate: string,) {}}export interface IProduct{prodid?: string | null;productName?: string;productDesc?:string;prodAddedDate?:string}

Import the model in services and create a product service class. Now create an add method that accepts product name, description, added date. The add product method generates product id randomly and returns product id when the product is added successfully.

将模型导入服务并创建产品服务类。 现在创建一个接受产品名称,描述,添加日期的添加方法。 添加产品方法会随机生成产品ID,并在成功添加产品后返回产品ID。

@Injectable()export class ProductsService {private products: IProduct[] = [];addProduct(productName:string,productDesc:string,productAddedDate:string) {const prodId = Math.random().toString();let product:IProduct = new Product(prodId,productName,productDesc,productAddedDate);this.products.push(product);return prodId;}}

In the product, the controller adds the following lines of code. NestJS provide inbuilt decorators, Post, and Body.

在产品中,控制器添加以下代码行。 NestJS提供内置的装饰器Post和Body。

@Post()addProduct(@Body(‘name’) productName: string,@Body(‘description’) productDesc: string,@Body(‘addedon’) productAddedDate: string,) {return this.productsService.addProduct(productName,productDesc,productAddedDate)}

Now when we insert some records, we will get record ids. Now time to get all products and a specific product.

现在,当我们插入一些记录时,我们将获得记录ID。 现在是时候获取所有产品和特定产品了。

For getting all products we can return a piece of products.

为了获得所有产品,我们可以退还一件产品。

getProducts() {return of([…this.products]);}

For getting a specific product we will write a get query. The user will provide id and search it and return the response.

为了获得特定产品,我们将编写一个get查询。 用户将提供ID并进行搜索,然后返回响应。

getProductById(productId: string) {console.log(productId);let index = this.products.findIndex(p=>p.prodid===productId);let searchProduct = index == 0 || index >0 ? this.products[index] : {}return of(searchProduct);}

To update the product search by product id and then update the record.

要通过产品ID更新产品搜索,然后更新记录。

updateProduct(productId: string, productName: string, productDesc: string, prodAddedDate: string) {const index = this.products.findIndex(p=>p.prodid===productId);var product :IProduct;if(index == 0 || index >0){product = { productName: productName, productDesc: productDesc,prodAddedDate: prodAddedDate}this.products[index]= product;}return of(product);}

For delete check the product by product id and splice from products.

要删除产品,请按产品ID和产品中的接头检查产品。

deleteProduct(productId: string) {const index = this.products.findIndex(p=>p.prodid===productId);return of(this.products.splice(index, 1));}

The complete product controller and services will look like this:

完整的产品控制器和服务将如下所示:

import { Injectable, NotFoundException } from '@nestjs/common';
import { Product, IProduct } from '../models/product';
import { of } from 'rxjs';
@Injectable()
export class ProductsService {
private products: IProduct[] = [];
addProduct(productName:string,productDesc:string,productAddedDate:string) {
const prodId = Math.random().toString();
let product:IProduct = new Product(prodId,productName,productDesc,productAddedDate);
this.products.push(product);
return prodId;
}
getProducts() {
return of([...this.products]);
}
getProductById(productId: string) {
console.log(productId);
let index = this.products.findIndex(p=>p.prodid===productId);
let searchProduct = index == 0 || index >0 ? this.products[index] : {}
return of(searchProduct);
}
updateProduct(productId: string, productName: string, productDesc: string, prodAddedDate: string) {
const index = this.products.findIndex(p=>p.prodid===productId);
var product :IProduct;
if(index == 0 || index >0)
{
product = { productName: productName, productDesc: productDesc,prodAddedDate: prodAddedDate}
this.products[index]= product;
}
return of(product);
}
deleteProduct(productId: string) {
const index = this.products.findIndex(p=>p.prodid===productId);
return of(this.products.splice(index, 1));
}
}import { Injectable, NotFoundException } from '@nestjs/common';
import { Product, IProduct } from '../models/product';
import { of } from 'rxjs';
@Injectable()
export class ProductsService {
private products: IProduct[] = [];
addProduct(productName:string,productDesc:string,productAddedDate:string) {
const prodId = Math.random().toString();
let product:IProduct = new Product(prodId,productName,productDesc,productAddedDate);
this.products.push(product);
return prodId;
}
getProducts() {
return of([...this.products]);
}
getProductById(productId: string) {
console.log(productId);
let index = this.products.findIndex(p=>p.prodid===productId);
let searchProduct = index == 0 || index >0 ? this.products[index] : {}
return of(searchProduct);
}
updateProduct(productId: string, productName: string, productDesc: string, prodAddedDate: string) {
const index = this.products.findIndex(p=>p.prodid===productId);
var product :IProduct;
if(index == 0 || index >0)
{
product = { productName: productName, productDesc: productDesc,prodAddedDate: prodAddedDate}
this.products[index]= product;
}
return of(product);
}
deleteProduct(productId: string) {
const index = this.products.findIndex(p=>p.prodid===productId);
return of(this.products.splice(index, 1));
}
}

import {
Controller,
Post,
Body,
Get,
Param,
Patch,
Delete,
Put,
} from '@nestjs/common';
import { ProductsService } from './products.service';
@Controller('products')
export class ProductsController {
constructor(private readonly productsService: ProductsService) {}
@Post()
addProduct(
@Body('name') productName: string,
@Body('description') productDesc: string,
@Body('addedon') productAddedDate: string,
) {

return this.productsService.addProduct(productName,productDesc,productAddedDate)
}
@Get()
getAllProducts() {
return this.productsService.getProducts();
}
@Get(':id')
getProduct(@Param('id') prodId: string) {
return this.productsService.getProductById(prodId);
}
@Put(':id')
updateProduct(
@Param('id') productId: string,
@Body('name') productName: string,
@Body('description') productDesc: string,
@Body('addedon') productAddedDate: string,
) {
return this.productsService.updateProduct(productId,productName,productDesc,productAddedDate);
}
@Delete(':id')
removeProduct(@Param('id') prodId: string) {
console.log('On delete');
console.log(prodId)
return this.productsService.deleteProduct(prodId);
}
}
邮递员的要求和回应 (Postman request and response)

Image for post
Image for post
Image for post
Image for post
Image for post
创建拦截器 (Creating Interceptor)

Interceptors are very similar to NodeJS middleware. So by any means, if we want to update the request, the response we can use interceptors. Interceptors are also used in the data messaging request-response. NestInterceptor comes in '@nestjs/common'. The DataInterceptor implements NestInterceptor.

拦截器与NodeJS中间件非常相似。 因此,无论如何,如果我们要更新请求,则可以使用拦截器来响应。 数据消息请求响应中也使用了拦截器。 NestInterceptor位于'@nestjs/common'DataInterceptor实现NestInterceptor

import {CallHandler,ExecutionContext,Injectable,NestInterceptor,NotFoundException} from '@nestjs/common';@Injectable()export class DataInterceptor implements NestInterceptor {intercept(context: ExecutionContext, next: CallHandler): Observable {}}

In the DataInterceptor we are simply checking the elapsed time between request and response and sending return in data. So the response will look like this.

在DataInterceptor中,我们只是在检查请求和响应之间以及发送数据返回之间所经过的时间。 因此响应将如下所示。

{"elapsed": 0,"data": [{"prodid": "0.931295133948634","productName": "Netgear Modem Number 3","productDesc": "Name2002460718 3","prodAddedDate": "01/01/2020"}]}

The complete data interceptor code will look like the below code.

完整的数据拦截器代码将类似于以下代码。

import {
    CallHandler,
    ExecutionContext,
    Injectable,
    NestInterceptor,
    NotFoundException
  } from '@nestjs/common';
  import { classToPlain } from 'class-transformer';
  import { Observable } from 'rxjs';
  import { map } from 'rxjs/operators';
 
  @Injectable()
  export class DataInterceptor implements NestInterceptor {
    intercept(context: ExecutionContext, next: CallHandler): Observable {
      const startTime = Date.now();
      return next.handle().pipe(
        map(data => {
          if (data == null) {
            return new NotFoundException();
          }
          const endTime = Date.now();
          const elapsed = endTime - startTime;
          return {
            elapsed,
            data: classToPlain(data)
          };
        })
      );
    }
  }

Now add the DataInterceptor in the root module as APP_INTERCEPTOR.

现在添加DataInterceptor根模块中APP_INTERCEPTOR

@Module({imports: [ ProductsModule],controllers: [AppController],providers: [AppService,{provide:APP_INTERCEPTOR,useClass:DataInterceptor}],})export class AppModule {}摘要 (Summary)

So we have discussed why we need NestJS to leverage API architecture. We have created NestJS CRUD API from scratch. We have a written data interceptor. This data interceptor intercepts request-response and adds elapse time and format the response automatically. Check the GitHub link fork the project and lear the NestJS.

因此,我们讨论了为什么需要NestJS来利用API体系结构。 我们从头开始创建了NestJS CRUD API。 我们有一个书面的数据拦截器。 该数据拦截器拦截请求响应,并添加经过时间并自动格式化响应。 检查GitHub链接fork项目并学习NestJS。

翻译自: https://medium.com/coding-in-depth/why-you-should-start-using-nestjs-ffb3fd3b8451

为什么用nestjs


推荐阅读
author-avatar
起薪d这帖
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有