概述
NestJS 是一个用于构建高效、可扩展的 Node.js 服务器端应用程序的渐进式框架。它基于 TypeScript 构建,但同时也支持纯 JavaScript 的开发。NestJS 结合了现代 JavaScript 特性和设计模式,如依赖注入、面向对象编程(OOP)、函数式编程(FP)等,提供了一个灵活且强大的开发环境。
本文将通过实际案例和代码示例,详细介绍如何使用 NestJS 框架进行开发。我们将涵盖从项目初始化到模块创建、路由定义、数据库连接、微服务集成等多个方面,帮助开发者快速掌握 NestJS 的核心概念和开发技巧。
安装与项目初始化
1. 安装 NestCLI
NestCLI 是官方提供的命令行工具,可以帮助我们快速创建和管理 NestJS 项目。首先,确保你已经安装了 Node.js 和 npm。然后,通过以下命令全局安装 NestCLI:
npm i -g @nestjs/cli
2. 创建新项目
使用 NestCLI 创建一个新的 NestJS 项目非常简单。只需运行以下命令:
nest new my-nestjs-app
这将启动一个交互式向导,帮助你选择项目的配置选项。默认情况下,NestCLI 会生成一个包含基本结构的 NestJS 项目,包括 src
目录、main.ts
入口文件、app.module.ts
根模块等。
3. 项目结构
一个典型的 NestJS 项目结构如下所示:
my-nestjs-app/
├── src/
│ ├── app.controller.ts
│ ├── app.module.ts
│ ├── app.service.ts
│ └── main.ts
├── test/
└── package.json
src/
:存放源代码文件。main.ts
:应用程序的入口文件。app.module.ts
:根模块,负责引导整个应用程序。app.controller.ts
和app.service.ts
:默认生成的控制器和服务类。
模块化开发
1. 创建模块
模块是 NestJS 中组织代码的基本单元。每个模块可以包含控制器、服务、守卫、拦截器、管道、异常过滤器等多种组件。通过模块化开发,我们可以将应用程序分解为多个小的、可重用的模块,从而提高代码的可维护性和可测试性。
使用 NestCLI 创建一个新模块非常简单。例如,创建一个名为 cats
的模块:
nest generate module cats
这将在 src/
目录下生成一个 cats.module.ts
文件,并将其自动导入到根模块中。
2. 模块结构
一个典型的模块结构如下所示:
// src/cats/cats.module.ts
import { Module } from '@nestjs/common';
import { CatsController } from './cats.controller';
import { CatsService } from './cats.service';
@Module({
controllers: [CatsController],
providers: [CatsService],
})
export class CatsModule {}
controllers
:定义模块中的控制器类。providers
:定义模块中的服务类和其他依赖项。
控制器与路由
1. 创建控制器
控制器负责处理 HTTP 请求并返回响应。每个控制器通常对应一组相关的路由。使用 NestCLI 创建一个控制器:
nest generate controller cats
这将在 src/cats/
目录下生成一个 cats.controller.ts
文件,并在 cats.module.ts
中自动注册该控制器。
2. 定义路由
在控制器中,我们可以使用装饰器来定义路由。例如:
// src/cats/cats.controller.ts
import { Controller, Get, Post, Body } from '@nestjs/common';
import { CatsService } from './cats.service';
@Controller('cats')
export class CatsController {
constructor(private readonly catsService: CatsService) {}
@Get()
findAll() {
return this.catsService.findAll();
}
@Post()
create(@Body() createCatDto: CreateCatDto) {
return this.catsService.create(createCatDto);
}
}
@Controller('cats')
:定义控制器的基础路径为/cats
。@Get()
和@Post()
:分别定义 GET 和 POST 请求的处理方法。@Body()
:提取请求体中的数据。
服务与业务逻辑
1. 创建服务
服务负责处理业务逻辑。使用 NestCLI 创建一个服务:
nest generate service cats
这将在 src/cats/
目录下生成一个 cats.service.ts
文件,并在 cats.module.ts
中自动注册该服务。
2. 实现业务逻辑
在服务中,我们可以编写具体的业务逻辑。例如:
// src/cats/cats.service.ts
import { Injectable } from '@nestjs/common';
@Injectable()
export class CatsService {
private readonly cats = [];
create(cat: any) {
this.cats.push(cat);
}
findAll(): any[] {
return this.cats;
}
}
@Injectable()
:标记服务类为可注入的依赖项。create
和findAll
:实现创建和查询猫的业务逻辑。
数据库连接
1. 安装 TypeORM
TypeORM 是一个流行的 ORM 库,支持多种数据库。首先,安装 TypeORM 和 MySQL 驱动:
npm install @nestjs/typeorm typeorm mysql2
2. 配置数据库连接
在 app.module.ts
中配置数据库连接:
// src/app.module.ts
import { Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { CatsModule } from './cats/cats.module';
@Module({
imports: [
TypeOrmModule.forRoot({
type: 'mysql',
host: 'localhost',
port: 3306,
username: 'root',
password: 'password',
database: 'test',
autoLoadEntities: true,
synchronize: true,
}),
CatsModule,
],
})
export class AppModule {}
3. 创建实体
实体表示数据库表。使用 NestCLI 创建一个实体:
nest generate entity cats/Cat
编辑生成的 cat.entity.ts
文件:
// src/cats/cat.entity.ts
import { Entity, Column, PrimaryGeneratedColumn } from 'typeorm';
@Entity()
export class Cat {
@PrimaryGeneratedColumn()
id: number;
@Column()
name: string;
@Column()
age: number;
@Column()
breed: string;
}
4. 使用实体
在 cats.module.ts
中引入实体:
// src/cats/cats.module.ts
import { Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { CatsController } from './cats.controller';
import { CatsService } from './cats.service';
import { Cat } from './cat.entity';
@Module({
imports: [TypeOrmModule.forFeature([Cat])],
controllers: [CatsController],
providers: [CatsService],
})
export class CatsModule {}
微服务集成
1. 安装微服务依赖
安装 gRPC 和 Redis 依赖:
npm install @nestjs/microservices grpc @grpc/proto-loader redis
2. 配置微服务客户端
在 app.module.ts
中配置微服务客户端:
// src/app.module.ts
import { Module } from '@nestjs/common';
import { ClientsModule, Transport } from '@nestjs/microservices';
import { CatsModule } from './cats/cats.module';
@Module({
imports: [
ClientsModule.register([
{
name: 'CAT_SERVICE',
transport: Transport.GRPC,
options: {
url: 'localhost:50051',
package: 'cat',
protoPath: join(__dirname, './cats/cats.proto'),
},
},
]),
CatsModule,
],
})
export class AppModule {}
3. 创建微服务服务器
创建一个微服务服务器:
// src/cats/cats.grpc.server.ts
import { NestFactory } from '@nestjs/core';
import { MicroserviceOptions, Transport } from '@nestjs/microservices';
import { CatsModule } from './cats.module';
async function bootstrap() {
const app = await NestFactory.createMicroservice<MicroserviceOptions>(
CatsModule,
{
transport: Transport.GRPC,
options: {
url: 'localhost:50051',
package: 'cat',
protoPath: join(__dirname, './cats/cats.proto'),
},
},
);
await app.listen();
}
bootstrap();
实战案例:构建 RESTful API
1. 创建用户模块
使用 NestCLI 创建一个用户模块:
nest generate module users
2. 创建用户控制器
创建用户控制器:
nest generate controller users
编辑 users.controller.ts
文件:
// src/users/users.controller.ts
import { Controller, Get, Post, Body } from '@nestjs/common';
import { UsersService } from './users.service';
@Controller('users')
export class UsersController {
constructor(private readonly usersService: UsersService) {}
@Get()
findAll() {
return this.usersService.findAll();
}
@Post()
create(@Body() createUserDto: CreateUserDto) {
return this.usersService.create(createUserDto);
}
}
3. 创建用户服务
创建用户服务:
nest generate service users
编辑 users.service.ts
文件:
// src/users/users.service.ts
import { Injectable } from '@nestjs/common';
@Injectable()
export class UsersService {
private readonly users = [];
create(user: any) {
this.users.push(user);
}
findAll(): any[] {
return this.users;
}
}
4. 创建用户实体
创建用户实体:
nest generate entity users/User
编辑 user.entity.ts
文件:
// src/users/user.entity.ts
import { Entity, Column, PrimaryGeneratedColumn } from 'typeorm';
@Entity()
export class User {
@PrimaryGeneratedColumn()
id: number;
@Column()
username: string;
@Column()
email: string;
@Column()
password: string;
}
5. 配置用户模块
在 users.module.ts
中引入实体:
// src/users/users.module.ts
import { Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { UsersController } from './users.controller';
import { UsersService } from './users.service';
import { User } from './user.entity';
@Module({
imports: [TypeOrmModule.forFeature([User])],
controllers: [UsersController],
providers: [UsersService],
})
export class UsersModule {}
结论
通过本文的介绍,我们详细学习了如何使用 NestJS 框架构建高效、可扩展的 Node.js 服务器端应用程序。从项目初始化到模块创建、路由定义、数据库连接、微服务集成等多个方面,我们掌握了 NestJS 的核心概念和开发技巧。希望这篇文章能够帮助你更好地理解 NestJS 并应用于实际项目中。