注意区别于nextJS框架——web全栈应用框架。
NestJS
NestJS 是一个现代的、用于构建可扩展的 Node.js 服务器端应用程序的框架,它使用 TypeScript 构建,结合了 OOP、FP 和 FRP (详见下面)。
NestJS 提供了一个开箱即用的应用架构,允许开发者和团队创建高度可测试、可扩展、松耦合且易于维护的应用 。适合构建大型、企业级的应用程序,其依赖注入系统、模块化和控制器的概念非常适合复杂的业务逻辑处理。
例如,在一个电子商务平台的后端服务中,NestJS 可以有效地组织商品管理、订单处理、用户认证等模块。
生态组件应用:
NestJS 支持广泛的第三方库和框架,如 Mongoose 用于 MongoDB 交互,TypeORM 用于数据库 ORM,以及 Passport 用于身份验证
它使用 Express.js 作为其底层的 Web 框架之一(另一个是 Fastify),因此 NestJS 应用程序天然地与 Express 集成。
NestJS 融合了多种编程范式,包括面向对象编程(OOP)、函数式编程(FP)和函数式反应式编程(FRP)。
NestJS 的设计哲学是将这些编程范式融合在一起,提供灵活性和强大功能,同时保持代码的清晰和可维护性。开发者可以根据自己的需求和喜好选择使用哪种范式,或者将它们结合起来构建 NestJS 应用程序。
以下是对这些范式的详细说明以及它们是如何在 NestJS 中体现的:
面向对象编程(OOP)
面向对象编程是一种编程范式,它使用“对象”来设计软件。对象可以包含数据(通常称为属性或字段)和代码(通常称为方法)。OOP 的核心概念包括:
- 封装:隐藏对象的内部状态和实现细节,只暴露出一个可以被外界访问和操作的接口。
- 继承:允许新创建的类(子类)继承现有类(父类)的属性和方法。
- 多态:允许不同类的对象对同一消息做出响应,但具体的行为会根据对象的实际类型而有所不同。
在 NestJS 中,OOP 的概念被广泛应用:
- 类和模块:NestJS 使用 TypeScript,一个支持 OOP 特性的语言,来定义类和模块。
- 依赖注入:NestJS 的依赖注入系统允许通过构造函数或方法参数传递对象,促进了模块化和代码重用。
函数式编程(FP)
函数式编程是一种编程范式,它将计算视为数学函数的评估,强调无副作用的函数和不可变数据。FP 的核心概念包括:
- 纯函数:给定相同的输入,总是返回相同的输出,没有可见的副作用。
无副作用:
副作用是指函数在执行过程中除了计算并返回值之外,对外部环境产生的任何影响。这可能包括修改全局变量、写入文件、修改数据库、抛出异常等。
- 不可变性:数据一旦创建就不能被改变,任何修改都会产生新的数据。
- 高阶函数:可以接受函数作为参数或返回函数的函数。
NestJS 支持 FP,提供了以下特性:
- 纯函数和不可变数据:NestJS 鼓励使用纯函数和不可变数据结构来构建应用。
- 高阶函数:NestJS 的很多内置功能,如管道(Pipes)和拦截器(Interceptors),都可以作为高阶函数使用。
函数式反应式编程(FRP)
函数式反应式编程是函数式编程的一个子集,专注于处理随时间变化的数据流。FRP 的核心概念包括:
- 响应式数据流:数据流是随时间变化的值,可以被观察和转换。
- 操作符:用于创建、查询、变换、组合和处理数据流的函数。
- 不可变和纯函数:FRP 通常使用不可变数据和纯函数来处理数据流。
举例:NestJS 通过 RxJS 库实现了 FRP:
- RxJS:NestJS 利用 RxJS 提供的响应式编程能力,允许开发者以声明性方式处理异步事件和数据流。
- 响应式库:NestJS 的很多服务和守卫(Guards)都可以使用 RxJS 操作符来响应和转换数据流。
使用 RxJS lastValueFrom
包装请求可以带来以下优化作用:
-
确保单个响应:
lastValueFrom
确保从请求中只获取最后一个响应值。这在控制请求的并发性时非常有用,特别是当你知道只需要最后一个响应。 -
防止请求泛滥:
如果请求的触发非常频繁,例如由于快速的输入或频繁的状态变化,使用lastValueFrom
可以防止发送过多的请求,只保留最后一个请求。 -
简化并发处理:
在处理多个并发请求时,lastValueFrom
可以帮助简化逻辑,只关注最后一个完成的请求结果。 -
提高性能:
通过取消之前的请求并只保留最后一个,可以减少不必要的网络负载和数据处理,从而提高应用程序性能。 -
避免竞态条件:
在某些情况下,如果多个请求几乎同时发出,可能会导致竞态条件。使用lastValueFrom
可以确保只处理最后一个请求的结果,避免这类问题。 -
与取消操作的兼容性:
lastValueFrom
可以与 RxJS 的取消操作(如takeUntil
或unsubscribe
)一起使用,以取消之前的请求。 -
错误处理:
如果请求失败,lastValueFrom
返回的 Promise 将被拒绝,这使得错误处理更加集中和一致。 -
与异步/等待的配合:
由于lastValueFrom
返回一个 Promise,它可以很容易地与async/await
语法一起使用,使得异步请求的编写和读取更加直观。 -
减少资源使用:
取消之前的请求可以减少对服务器资源的使用,特别是在服务器端处理请求成本较高的情况下。 -
改善用户体验:
通过只处理最后一个请求,可以确保用户界面显示的数据是最新的,避免因旧请求的响应而产生混淆。
使用 lastValueFrom
包装请求是一种有效的方法,可以优化请求管理,特别是在处理复杂的异步