Vue3 + Nest 实现权限管理系统 后端篇(一):NestJS入门与基础配置(上)

本文涉及的产品
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 RDS PostgreSQL,集群系列 2核4GB
简介: Vue3 + Nest 实现权限管理系统 后端篇(一):NestJS入门与基础配置(上)

image.png

NestJS 是一个 NodeJS 的后端服务框架,它与传统的 NodeJS 框架不一样的是采用了控制反转(IOC)和依赖注入(DI)的模式进行开发,当然如果你对这中开发模式不熟悉的话也没关系,你可以查找资料去了解这种模式,或者直接开始阅读本篇文章你就会用 NestJS 了(会用就行)。接下来我们开始介绍 NestJS


全局安装 NestJS



npm i -g @nestjs/cli


第一个 NestJS 程序



nest new management_nest

执行完毕就会看到 src 下有这样一个目录

image.png

  • app.controller.ts

这里控制层,这里主要是写路由相关代码以及处理前端传来的一些参数(后面文章会介绍如何接收参数)

import { Controller, Get } from '@nestjs/common';
import { AppService } from './app.service';
@Controller()
export class AppController {
  constructor(private readonly appService: AppService) {}
  @Get()
  getHello(): string {
    return this.appService.getHello();
  }
}
  • app.service.ts

这里是业务层,在这里写一些与业务相关的逻辑。比如对数据库的 CRUD 就可以写到这里

import { Injectable } from "@nestjs/common";
@Injectable()
export class AppService {
  getHello(): string {
    return "Hello World!";
  }
}
  • app.module.ts

它可以组织应用程序中的许多功能,如控制器、服务以及可以导入其他模块等

import { Module } from "@nestjs/common";
import { AppController } from "./app.controller";
import { AppService } from "./app.service";
@Module({
  imports: [],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}
  • main.ts
import { NestFactory } from "@nestjs/core";
import { AppModule } from "./app.module";
async function bootstrap() {
  const app = await NestFactory.create(AppModule);
  await app.listen(3000);
}
bootstrap();

main.ts 则是整个程序的入口文件

我们可以执行pnpm run start:dev开启一个可以热更新的 NestJS 服务,浏览器打开http://localhost:3000/便可发送一个 get 请求到app.controller.ts中的 getHello 函数,然后再调用app.service.ts里的 getHello 函数返回Hello World!

image.png

这里我们发现app.controller.ts的 appService 并没有实例化就可以直接使用了,其实这里是因为在app.module.ts已经进行了依赖注入(providers)这里已经将其处理好了


装饰器



在上面的代码中我们看到了譬如@Controller(),@get(),@Module()之类的东西,其实这些东西就是装饰器,你可以把它看作一个函数就行了,比如@Controller()它属于一个类装饰器,他会把下面的类当作参数传入然后进行一些处理从而实现处理路由的功能

为了更好的演示,我们新建一个模块,NestJS 给我们提供了一些命令可以创建对应文件,比如

  • 生成一个 module (nest g mo) 。
  • 生成一个 controller (nest g co) 。
  • 生成一个 service (nest g s) 。

你可以执行nest -h 查看这些命令

我们可以执行nest g res user生成一个 user 模块,包括它的module,controller,service,执行之前可以在nest-cli.json中配置

"generateOptions": {
    "spec": false
  }

让其不生成测试文件,执行命令我们可以选择 REST API 的形式,这样我们 src 下就会出现了 user 模块

我们可以看到user.controller.ts引入了很多装饰器,已经给我们写好了 CRUD 的模板

import {
  Controller,
  Get,
  Post,
  Body,
  Patch,
  Param,
  Delete,
} from '@nestjs/common';
import { UserService } from './user.service';
import { CreateUserDto } from './dto/create-user.dto';
import { UpdateUserDto } from './dto/update-user.dto';
@Controller('user')
export class UserController {
  constructor(private readonly userService: UserService) {}
  @Post()
  create(@Body() createUserDto: CreateUserDto) {
    return this.userService.create(createUserDto);
  }
  @Get()
  findAll() {
    return this.userService.findAll();
  }
  @Get(':id')
  findOne(@Param() id: string) {
    return this.userService.findOne(+id);
  }
  @Patch(':id')
  update(@Param('id') id: string, @Body() updateUserDto: UpdateUserDto) {
    return this.userService.update(+id, updateUserDto);
  }
  @Delete(':id')
  remove(@Param('id') id: string) {
    return this.userService.remove(+id);
  }
}

@Post,@Get,@Patch等就是对应的请求方式装饰器,比如你用 POST 请求调用http://localhost:3000/user就会进入@Post()下面的 create()方法,@Body,@Params则是请求参数装饰器,我们可以从中获取到前端传来的参数

拿第一个Post请求举例,发送 post 请求我们可以使用postman,apifox等工具进行测试,这里我使用apifox进行演示

我们可以先打印一下前端@Body()装饰的createUserDto,然后发送一个 Post 请求

@Post()
  create(@Body() createUserDto: CreateUserDto) {
    console.log(createUserDto);
    return this.userService.create(createUserDto);
  }

image.png

此时我们就会发现控制台打印了前端传来的 Body 参数

image.png

如果想使用别的请求路径,可以在@Post 传入路径,比如@Post('list'),请求路径就会变成/user/list


如果你想获取 Get 请求传来的参数可以使用@Query,获取 Header 中的参数可以使用@Header 等等,这些装饰器有很多这里就不过多介绍了,后面的教程中遇到会作一个详细说明


连接 MySql 数据库



作为一个后端框架肯定是离不开数据库的,NestJS 连接数据库其实很简单,可以先安装@nestjs/typeormmysql,typeorm可以让对数据库的 sql 操作映射成对象的操作

pnpm install @nestjs/typeorm typeorm mysql -S

然后你需要在本地安装 mysql 数据库,这里可以自行百度~(注意记住你的用户名和密码以及数据库安装位置)

推荐一个 VSCode 数据库可视化插件Database Client,安装完后连接我们的数据库就能进行一个可视化操作

image.png

一切准备就绪,我们新建一个数据库名为easyestadmin,然后开始连接 mysql,我们来到app.module.ts中进行数据库的配置,引入TypeOrmModule调用forRoot进行配置

import { Module } from "@nestjs/common";
import { AppController } from "./app.controller";
import { AppService } from "./app.service";
import { UserModule } from "./user/user.module";
import { TypeOrmModule } from "@nestjs/typeorm";
@Module({
  imports: [
    TypeOrmModule.forRoot({
      type: "mysql",
      synchronize: true,
      autoLoadEntities: true, //自动加载实体
      host: "localhost",
      port: 3306, // 端口号
      username: "root", // 用户名
      password: "root", // 密码
      database: "management", //数据库名
      synchronize: true, //是否自动同步实体文件,生产环境建议关闭
    }),
    UserModule,
  ],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}

当我们将autoLoadEntities设置为 true 的时候,NestJS 会自动加载数据库实体文件xx.entity.ts文件来创建数据表(如果没有的话),比如 user/entities/user.entity.ts,我们简单加一些字段

import { Column, Entity, PrimaryGeneratedColumn } from "typeorm";
@Entity("user")
export class User {
  @PrimaryGeneratedColumn("uuid")
  id: number; // 标记为主键,值自动生成
  @Column({ length: 30 })
  username: string; //用户名
  @Column()
  password: string; //密码
}

启动项目,然后就会发现自动创建了一个 user 表

image.png

如果我们想对 user 表进行一些 CRUD 的操作.可以在user.module.ts中导入

import { Module } from "@nestjs/common";
import { UserService } from "./user.service";
import { UserController } from "./user.controller";
import { User } from "./entities/user.entity";
import { TypeOrmModule } from "@nestjs/typeorm";
@Module({
  controllers: [UserController],
  providers: [UserService],
  imports: [TypeOrmModule.forFeature([User])],
})
export class UserModule {}

user.service.ts中引入使用,比如在 create 函数中创建一条数据

import { Injectable } from "@nestjs/common";
import { CreateUserDto } from "./dto/create-user.dto";
import { UpdateUserDto } from "./dto/update-user.dto";
import { User } from "./entities/user.entity";
import { InjectRepository } from "@nestjs/typeorm";
import { Repository } from "typeorm";
@Injectable()
export class UserService {
  constructor(
    @InjectRepository(User)
    private userRepository: Repository<User>
  ) {}
  async create(createUserDto: CreateUserDto) {
    return await this.userRepository.save(createUserDto);
  }
  async findAll() {
    return await this.userRepository.find();
  }
  findOne(id: number) {
    return `This action returns a #${id} user`;
  }
  update(id: number, updateUserDto: UpdateUserDto) {
    return `This action updates a #${id} user`;
  }
  remove(id: number) {
    return `This action removes a #${id} user`;
  }
}

再调用 user 接口,传入 username 和 password

image.png

我们就完成了一条数据的插入,在 findAll 中查询所有数据,调用 get 请求便可拿到 user 表中的数据

image.png

一般来说数据库的配置包含了一些敏感信息不宜写在代码中提交到远程仓库,所以我们可以将配置写在配置文件中,然后提交 git 时候将生产环境的配置文件其忽略,这里我们新建.env.env.prod两个文件分别存放开发与生产环境配置

我们还安装 cross-env 来判断我们是处于什么环境

pnpm install cross-env

然后修改package.json中的script

"start:prod": "cross-env NODE_ENV=production node dist/main",

这样我们生成环境的 NODE_ENV 就是 production 了,我们可以根据这个加载不同配置文件。想要加载配置文件,NestJS 给我们提供了@nestjs/config,这个需要手动安装,安装完成之后,在app.module.ts进行配置

import { Module } from "@nestjs/common";
import { AppController } from "./app.controller";
import { AppService } from "./app.service";
import { UserModule } from "./user/user.module";
import { TypeOrmModule } from "@nestjs/typeorm";
import { ConfigModule } from "@nestjs/config";
import * as path from "path";
const isProd = process.env.NODE_ENV == "production";
@Module({
  imports: [
    ConfigModule.forRoot({
      envFilePath: [isProd ? path.resolve(".env.prod") : path.resolve(".env")],
    }),
    TypeOrmModule.forRoot({
      type: "mysql",
      host: process.env.DB_HOST,
      port: parseInt(process.env.DB_PORT), // 端口号
      username: process.env.DB_USER, // 用户名
      password: process.env.DB_PASSWD, // 密码
      autoLoadEntities: true, //自动加载实体
      synchronize: !isProd, //是否自动同步实体文件,生产环境建议关闭
      database: process.env.DB_DATABASE, //数据库名
    }),
    UserModule,
  ],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}


相关实践学习
如何在云端创建MySQL数据库
开始实验后,系统会自动创建一台自建MySQL的 源数据库 ECS 实例和一台 目标数据库 RDS。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助 &nbsp; &nbsp; 相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
26天前
|
JavaScript 数据可视化
vue-cli学习二:vue-cli3版本 创建vue项目后,Runtime-Compiler和Runtime-only两个模式详解;vue项目管理器;配置文件的配置在哪,以及如何配置
这篇文章详细介绍了Vue CLI 3版本创建项目时的Runtime-Compiler和Runtime-only两种模式的区别、Vue程序的运行过程、render函数的使用、eslint的关闭方法,以及Vue CLI 2和3版本配置文件的不同和脚手架3版本创建项目的配置文件配置方法。
30 3
vue-cli学习二:vue-cli3版本 创建vue项目后,Runtime-Compiler和Runtime-only两个模式详解;vue项目管理器;配置文件的配置在哪,以及如何配置
|
9天前
|
JavaScript 前端开发 开发者
如何在 Visual Studio Code (VSCode) 中使用 ESLint 和 Prettier 检查代码规范并自动格式化 Vue.js 代码,包括安装插件、配置 ESLint 和 Prettier 以及 VSCode 设置的具体步骤
随着前端开发技术的快速发展,代码规范和格式化工具变得尤为重要。本文介绍了如何在 Visual Studio Code (VSCode) 中使用 ESLint 和 Prettier 检查代码规范并自动格式化 Vue.js 代码,包括安装插件、配置 ESLint 和 Prettier 以及 VSCode 设置的具体步骤。通过这些工具,可以显著提升编码效率和代码质量。
109 4
|
13天前
|
资源调度 JavaScript 前端开发
路由管理:Vue Router的使用和配置技巧
【10月更文挑战第21天】路由管理:Vue Router的使用和配置技巧
28 3
|
21天前
|
存储 前端开发 中间件
vue3之vite配置vite-plugin-mock使用mock轻松创建模拟数据提高开发效率
vue3之vite配置vite-plugin-mock使用mock轻松创建模拟数据提高开发效率
149 0
|
22天前
|
存储 缓存 监控
构建高效后端系统的关键要素
【10月更文挑战第12天】 本文将探讨如何通过合理的架构设计、数据库优化、缓存策略和性能调优等措施,构建一个稳定、高效的后端系统。我们将分享一些实用的技巧和最佳实践,帮助开发者提升后端系统的性能和用户体验。
28 1
|
24天前
|
存储 JavaScript 前端开发
前端开发:Vue.js入门与实战
【10月更文挑战第9天】前端开发:Vue.js入门与实战
|
26天前
|
JavaScript API 开发者
十分钟 带你强势入门 vue3
十分钟 带你强势入门 vue3
60 1
|
1月前
|
存储 缓存 测试技术
构建高效后端系统的关键策略##
【10月更文挑战第2天】 在当今数字化时代,后端系统的性能和可扩展性对于任何技术驱动的企业都至关重要。本文将深入探讨如何通过优化数据库设计、实施缓存机制、采用微服务架构以及自动化测试等措施,构建一个既高效又可靠的后端系统。我们将从基础的代码优化开始,逐步讨论到架构级别的改进,最终目标是提供一个全面的指导方案,帮助开发者和企业提升其后端系统的性能和可维护性。 ##
48 2
|
1月前
|
数据可视化 测试技术 Linux
基于Python后端构建多种不同的系统终端界面研究
【10月更文挑战第10天】本研究探讨了利用 Python 后端技术构建多样化系统终端界面的方法,涵盖命令行界面(CLI)、图形用户界面(GUI)及 Web 界面。通过分析各种界面的特点、适用场景及关键技术,展示了如何使用 Python 标准库和第三方库(如 `argparse`、`click`、`Tkinter` 和 `PyQt`)实现高效、灵活的界面设计。旨在提升用户体验并满足不同应用场景的需求。
|
12天前
|
JavaScript 前端开发 C#
从入门到放弃,我们为何从 Blazor 回到 Vue
【10月更文挑战第29天】在前端开发中,许多开发者从尝试新技术 Blazor 最终回到熟悉的 Vue。主要原因包括:1) Blazor 学习曲线陡峭,Vue 上手容易;2) Vue 开发工具成熟,开发效率高;3) Vue 性能优异,优化简单;4) Vue 社区庞大,生态丰富;5) 项目需求和团队协作更适配 Vue。选择技术栈需综合考虑多方面因素。