前言
对于有经验的前端开发人员来说,使用 Sequelize 来操作数据库可能已经成了家常便饭。Sequelize 是一个 Node.js ORM 框架,提供了强大的数据库操作功能和灵活的数据模型定义方式。但是,在实际项目开发中,Sequelize 对于复杂的查询操作并不是非常友好,需要使用很多查询条件,而且代码冗长。为了解决这个问题,开源社区中出现了很多类库,其中最出名的包括 Sequelize-Plus、sequelize-op、sequelize-paginate 等,它们在增加查询操作的便利性方面都做出了很多努力。其中最受欢迎的包之一就是 sequelize-builder。
sequelize-builder 是一个 Sequelize 查询构建器,它扩展了 Sequelize 的查询机制并使用面向对象的方式提供了一种方便的方式来构建复杂查询,这对于大规模项目的开发来说可以提升效率和代码质量。在这篇文章中,我们将详细探讨 sequelize-builder 的使用方式和技术原理。
安装
在你准备使用 sequelize-builder 之前,你需要先引入 Sequelize,然后通过以下方式安装 sequelize-builder:
npm install sequelize-builder
演示
我们将通过以下的例子来演示如何使用 sequelize-builder 构建复杂查询。
假设我们需要查询一个商城网站的订单信息。商城包含很多不同的产品类别,每个类别下面有很多不同的商品,但是客户只会看到商品类别的名称而不会看到商品的名称。我们需要为该商城编写查询代码,它可以按照以下条件进行过滤:
选择订单状态为已支付的订单
按照订单创建时间降序排列
检索订单的商品类别名称,而不是商品的名称
使用 sequelize-builder,可以如下实现:
-- -------------------- ---- ------- ----- - ------------------- ------------- ------------- ------------- --------------- ------------- - - ----------------------------- -- ------ ---- --------- ------ ----- ----- - ------------------------- - --- --- ----- --------------- - ----------------------------------- - --- --- ----- ------- - --------------------------- - --- --- -- --------- --- ----- ------- ----- ------- - --- -------------------------- --------------------- -------------- ----------------- ---------------------------- ---- --------- ----------------- ------------------------------ ------- ------------------- ---------------------------------------------- ----------- ------------------- -------------------------------------- --------- -- ------- --- ----- ------- ------- ---------- -------------- -- -------------------- -------------- -- ----------------------
在这个代码片段中,我们首先定义了我们要查询的三个 Sequelize 模型:Order、ProductCategory 和 Product。然后我们实例化了一个 SelectQueryBuilder,并调用了它的 select、where、order、include 和 limit 方法来构建查询。最后,我们通过调用 execute 方法来执行查询,查询结果会被传入一个 Promise 回调中。
这个查询会首先选择 Order 模型的 id 和 createdAt 属性,然后使用一个 WhereBuilder 对象来定义查询条件,筛选出订单状态为 "paid" 的所有订单,这样就按照第一点要求完成了查询过滤。接着,我们使用 OrderBuilder 对象来按照订单创建时间降序排列,实现了第二点要求。然后我们定义了两个 IncludeBuilder 对象来处理关联模型,前者将 ProductCategory 模型作为关联模型,并取别名为 category。后者将 Product 模型作为关联模型,并取别名为 products。在这种查询方式下,您可以在查询结果中找到包含 category 和 product 数据的订单记录。最后,我们使用 execute 方法来实际执行查询,将结果传递给一个回调处理函数。
接下来,我们可以通过调用 builder.toSql() 来查看生成的 SQL 语句:
-- -------------------- ---- ------- ------ ------------- -------------------- ----------------- -- ---------------- --------------- -- ------------- ---- -------- -- ------- ---- ----- ---- ------------------- -- ---------- -- -------------------- - --------------- ---- ----- ---- ---------- -- ---------- -- ------------ - -------------------- ----- -------- - ------ ----- -- ----------- ----
概念 & Api详解
1. QueryBuilder
QueryBuilder 是 sequelize-builder 的核心对象,用于构建查询。QueryBuilder 对象通过选择 Sequeilize 模型,设置查询条件、包含模型等等来生成应该执行的 SQL 查询语句。
1.1 select
select(attributes: Array<string>): QueryBuilder
使用 select 方法来配置 SELECT 语句包含的属性。使用它的参数中添加属性名的数组来定义需要被选择的字段。
builder.select(['id', 'name']);
1.2 where
where(builderOrConditions: WhereBuilder | Sequelize)
使用 where 方法来配置 WHERE 语句中使用的条件。BuilderOrConditions 参数可以是一个 WhereBuilder 对象或 Sequelize 的查询条件。
如果你选择使用 WhereBuilder,你将能够使用 AND 和 OR 操作符。例如:
const whereBuilder = new WhereBuilder() .and('status', '=', 'success') .or('status', '=', 'in_process'); builder.where(whereBuilder);
如果你想要使用一个简单的条件,例如:
builder.where({ status: 'success' });
1.3 order
order(order: OrderBuilder): QueryBuilder
使用 order 方法来配置 ORDER BY 子句的属性和排序方式,OrderBuilder 参数允许你指定排序的属性、排序方式以及 ASC 或 DESC。
const orderBuilder = new OrderBuilder().by('createdAt', true); // true 表示降序排列 builder.order(orderBuilder);
1.4 include
include(includedModel: IncludeBuilder): QueryBuilder
使用 include 方法来配置 IncludeBuilder 实例中的关联。IncludeBuilder 封装了要查询的关联模型和关联的查询条件。
const productCategoryInclude = new IncludeBuilder(ProductCategory) .as('category', ['name']); const productInclude = new IncludeBuilder(Product) .as('products', ['id']); builder.include(productCategoryInclude); builder.include(productInclude);
1.5 limit
limit(limit: number): QueryBuilder
使用 limit 方法来配置 LIMIT 子句,用于限制查询结果的数量。
builder.limit(10);
1.6 withTransaction
withTransaction(transaction: SequelizeTransactionalStatic): QueryBuilder
如果您的查询需要在 Sequelize 事务中运行,您可以通过 withTransaction 方法来指定。传递 Sequelize 的事务对象到这个方法中。
注意:这个方法仅在配置了 Sequelize 实例的情况下才能使用。
2. WhereBuilder
WhereBuilder 是一个使用面向对象风格的接口来创建 Sequelize 的查询条件对象的实用工具类。下面是 WhereBuilder 能够使用的操作符:
and(column: string, operator: string, value: any): WhereBuilder
or(column: string, operator: string, value: any): WhereBuilder
in(column: string, values: Array<any>): WhereBuilder
notIn(column: string, values: Array<any>): WhereBuilder
like(column: string, pattern: string): WhereBuilder
notLike(column: string, pattern: string): WhereBuilder
between(column: string, start: any, end: any): WhereBuilder
notBetween(column: string, start: any, end: any): WhereBuilder
gt(column: string, value: any): WhereBuilder
gte(column: string, value: any): WhereBuilder
lt(column: string, value: any): WhereBuilder
lte(column: string, value: any): WhereBuilder
以下是一个 WhereBuilder 的例子:
const whereBuilder = new WhereBuilder() .and('id', '>', 3) .or('name', 'like', '%John%');
3. OrderBuilder
OrderBuilder 是一个使用面向对象风格的接口来构建排序对象的实用工具类。以下是 OrderBuilder 的例子:
const orderBuilder = new OrderBuilder().by('createdAt', true); // true 表示降序排列
4. IncludeBuilder
IncludeBuilder 是一个使用面向对象风格的接口来构建包含关联模型的实用工具类。使用 include 方法将其添加到 QueryBuilder 发送的 SQL 语句中。以下是 IncludeBuilder 的例子:
const productInclude = new IncludeBuilder(Product) .as('products', ['id']);
5. SelectQueryBuilder
SelectQueryBuilder 是一种使用 Sequelize 的 SELECT 查询命令并且扩展了它的查询语句的公用对象。查询将被构建为 Sequelize 的查询格式。
5.1 execute
execute(): Promise
execute 方法实际执行查询,并将其结果返回到一个 Promise 中。
5.2 toSql
toSql(): string
toSql 方法生成可执行的 SQL 查询,并返回 SQL 查询语句的字符串表示形式。
const sql = builder.toSql(); console.log(sql);
结论
sequelize-builder 是一个非常有用的 Node.js 模块,在开发基于 Sequelize 库的 Node.js 应用程序时,通过使用它,您可以轻松地构建复杂的查询语句。sequelize-builder 的好处在于,它提供了可读性强的、面向对象的语法来简化查询构造过程,使开发人员能够更快的完成开发任务。无论您是初学 Sequelize 还是经验丰富的开发人员,都能发现 sequelize-builder 能够为您的项目带来很大的便利性。
参考资料
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/60067355890c4f7277583ae2