Sequelize 在 Egg.js 上实践与优化

阅读时长 14 分钟读完

Sequelize 在 Egg.js 上实践与优化

Sequelize 是一个 Node.js 中的 ORM(对象关系映射工具),它允许我们使用 JavaScript 代码来操作关系数据库。而 Egg.js 则是一款企业级的基于 Node.js 的开发框架。本文主要介绍如何在 Egg.js 中使用 Sequelize,并在此基础上进行一些优化。

一、Sequelize 在 Egg.js 中的基本使用

1.1 安装 Sequelize 和 Sequelize-cli

在项目根文件夹中执行以下命令:

1.2 配置 Sequelize

在 config/config.default.js 中配置 sequelize。

-- -------------------- ---- -------
-------------- - -
  ---------- -
    -------- --------
    ----- ------------
    ----- -----
    --------- --------
    --------- -------
    --------- ---------
    ------- -
      --------- -----
      ------------ -----
      ---------------- -----
      -------- ----------
      --------------- -
        -------- --------------------
      -
    -
  -
-
展开代码

其中,dialect 表示使用的数据库种类,host 表示数据库地址,port 表示数据库端口,database 表示数据库名称,username 和 password 表示登录数据库的用户名和密码。

1.3 使用 Sequelize

通过 sequelize.import() 方法就可以导入 Sequelize 的 Model。下面是一个简单的例子:

定义模型:

-- -------------------- ---- -------
-- -----------------
-------------- - --- -- -
  ----- - ------- ------- - - --------------
  ----- ---- - ------------------------ -
    --- - ----- --------------------- ----------- ----- -------------- ----- -------- ------ --
    ----- -----------
    ---- --------
  -- -
    ----------- ------
    -------- ------
    ---------- --------
    -------- -
      -
        ------- -----
        ------- --------
      --
    -
  --
  ------ -----
-
展开代码

使用模型:

-- -------------------- ---- -------
-- ----------------------
----- ---------- - --------------------------

----- -------------- ------- ---------- -
  ----- -------- -
    ----- - --- - - -----
    ----- ---- - ----- -----------------------
      ----- -------
      ---- ---
    ---
    -------- - -
      -----
    --
  -
  ----- ------ -
    ----- - --- - - -----
    ----- ----- - ----- -------------------------
    -------- - -
      ------
    --
  -
-

-------------- - ---------------
展开代码

1.4 Sequelize-hook

sequelize-hook 是对 Sequelize 的增强,它提供了一组模型钩子方法(类似于 Mongoose 的中间件),可以在模型的生命周期中进行一些操作。比如为每个模型增加 createdAt 和 updatedAt 字段,简化 SQL 编写,如果模型中有 deleteAt 的话可以自动伪删除数据。

安装 sequelize-hook:

使用 sequelize-hook:

-- -------------------- ---- -------
-- -----------------
-------------- - --- -- -
  ----- - ------- ------- - - --------------
  ----- ----- - --------------------------
  ----- ---- - ------------------------ -
    --- - ----- --------------------- ----------- ----- -------------- ----- -------- ------ --
    ----- -----------
    ---- --------
  -- -
    ----------- ------
    -------- ------
    ---------- --------
    -------- -
      -
        ------- -----
        ------- --------
      --
    --
    ------ -
      ------------- ---------------------
      ------------- ---------------------
      ----------------- -------------------------
      ----------------- -------------------------
      -------------- ------------------------------
      ------------------ ---------------------------------
    -
  --
  ------ -----
-
展开代码

二、Sequelize 在 Egg.js 中的进阶使用

2.1 大批量插入数据

当需要插入大量数据时,我们通常使用 bulkCreate 方法,它可以一次插入多条数据,避免多次向数据库发起请求,提高性能。但是在 Egg.js 中,bulkCreate 的性能仍然不尽如人意,原因是它在数据量较大的情况下会卡死 Node.js 的事件循环,从而导致应用不能处理任何请求。解决方法是使用 Sequelize-bulk-create,它可以让 bulkCreate 异步执行,不会阻塞事件循环。

安装 Sequelize-bulk-create:

使用 Sequelize-bulk-create:

-- -------------------- ---- -------
-- -----------------
-------------- - --- -- -
  ----- - ------- ------- - - --------------
  ----- ----- - --------------------------
  ----- ------------------- - ----------------------------------------
  ----- ---- - ------------------------ -
    --- - ----- --------------------- ----------- ----- -------------- ----- -------- ------ --
    ----- -----------
    ---- --------
  -- -
    ----------- ------
    -------- ------
    ---------- --------
    -------- -
      -
        ------- -----
        ------- --------
      --
    --
    ------ -
      ------------- ---------------------
      ------------- ---------------------
      ----------------- -------------------------
      ----------------- -------------------------
      -------------- ------------------------------
      ------------------ ---------------------------------
    -
  --

  -- --------
  -------------------- - -------- ------ ------- - --- -
    ------ ------------------------- ----- ---------
  -

  ------ -----
-
展开代码

调用方式:

-- -------------------- ---- -------
-- ----------------------
----- ---------- - --------------------------

----- -------------- ------- ---------- -
  ----- -------------- -
    ----- - --- - - -----
    ----- ----- - --
      ----- ----
    ---
      ----- ----
    ---
      ----- ----
    --
    ----- -------------------------------------
    -------- - -
      ------
    --
  -
-

-------------- - ---------------
展开代码

2.2 Sequelize 配合 GraphQL

在 Egg.js 中配置 GraphQL 需要用到 graphql、graphql-tools、apollo-server-koa 这几个库。

安装依赖:

编写 GraphQL 类型:

-- -------------------- ---- -------
-- ---------------------
----- - --- - - -----------------------------

----- -------- - ----
  ---- ---- -
    --- ---
    ----- -------
    ---- ----
  -
  ---- ----- -
    -------- ----- -----
    ------ -------
  -
--

-------------- - ---------
展开代码

定义 Query:

-- -------------------- ---- -------
-- ------------------------
----- --------- - -
  ------ -
    ----- ------- ----- ------ -
      ----- ---- - ----- ---------------------------
      ------ -------------
    --
    ----- -------- --- ------ -
      ----- ----- - ----- ------------------------
      ------ ------------------------      
    --
  --
--

-------------- - ----------
展开代码

配置 ApolloServer:

-- -------------------- ---- -------
-- ---------------------
----- - ------------ - - -----------------------------
----- -------- - --------------------
----- --------- - -----------------------

----- ------ - --- --------------
  ---------
  ----------
  -------------- -----
  ----------- -----
  -------- ----- -- --- -- -- -
    ------ - --- --
  --
---

-------------- - -------
展开代码

在 app.js 中使用 ApolloServer:

三、Sequelize 在 Egg.js 中的性能优化

3.1 数据库连接池

数据库连接池可以优化数据库访问性能。Sequelize 默认提供了数据库连接池,只需在 config/config.default.js 中添加以下配置即可。

-- -------------------- ---- -------
-------------- - -
  ---------- -
    --- ---
    ----- -
      ---- --
      ---- --
      ----- -----
    --
    --- --
  --
--
展开代码

其中,pool.max 表示连接池最大连接数,pool.min 表示连接池最小连接数,pool.idle 表示连接保持活跃状态的时间。

3.2 数据库读写分离

应用在高并发、大流量的情况下,数据库读写压力可能会非常大。在这种情况下,可以考虑对数据库进行读写分离优化。Sequelize 并不支持自动的读写分离,需要借助一些第三方库,比如 sequelize-read-support,它提供了透明的读写分离功能。读写分离使用 master-slave 架构,写操作只在 master 数据库中进行,读操作则可在 slave 数据库中进行。

安装依赖:

使用方式:

-- -------------------- ---- -------
-- ------------------------
----- ----------- - ----------------------------------
-------------- - -
  ---------- -
    --- ---
    ------ -
      ---- -
    --
    --------- -----------------
    --------- ------
    --------- ------
    ----- ------------
    ----- -
      - ----- ------------ --------- ------ --------- -------
      - ----- -------------- --------- ------ --------- -------
      - ----- -------------- --------- ------ --------- ------
    --
    ------ - ----- ------------ --------- ------ --------- ----- --
    -------- --------
    ------- -
      ----------- ------
      ---------------- ----
    --
    -------- ------------
    ----- -
      ---- ---
      ---- --
      ----- -----
    --
    ----------------- -------------
    ----- -
      ------ -----
    --
    ------ -
      ---- -
    -
  -
--

----- ------- - --- -----------------------
----- ---- - ---------------
---------------------- - ------ ---- ---
展开代码

通过将配置中的 read 选项值设置为一个数组,可以实现在多个数据库之间进行均衡的负载分配。write 选项值表示写入操作的数据库,可以分离出来以分担主库的压力。在 Egg.js 框架中使用 Sequelize 时,可以借助 sequelize-read-support 实现方便的读写分离。

总结

本文介绍了 Sequelize 在 Egg.js 中的基本用法以及一些优化技巧,包括大批量插入数据、响应 GraphQL 查询、数据库连接池和读写分离。在实际开发过程中,这些技巧能够大大提高应用的性能和可

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/6548d7307d4982a6eb318c91

纠错
反馈

纠错反馈