Koa 中使用 MySQL 数据库

发布于 2022-01-27 22:10:33 字数 3201 浏览 1549 评论 0

封装思路

koa 依赖 co,其中间件对非阻塞异步代码的要求必须是 Yieldables 列表中的形式,而 mysql 库是回调函数的形式。因此,我们需要进行封装,使其接口符合要求。

目前我找到了四种方法,前三种使用开源库,第四种自己动手,将 express 下的 dbHelper 层封装成 co 最新支持的 Promise 形式。

实现方法一(co-mysql)

co-mysql 和 mysql-co 实现了对 mysql 或 mysql2 的封装转化。这两个库的思路差不多,mysql-co 封装度更高,并使用速度更快的 mysql2;而 co-mysql 更简单,只是将 mysql.query 封装成 Promise 形式。下面是基于 co-mysql 的示例代码:

var wrapper = require('co-mysql'),
  mysql = require('mysql');
var options = { /* 数据库连接字串 */ };

var pool = mysql.createPool(options),
  p = wrapper(pool);

...
  var rows = yield p.query('SELECT 1');
  yield this.render('index', {
    title: rows[0].fieldName
  });
...
})();

实现方法二(promisify-node)

使用 promisify-node 库,可以将库整体转化为 Promise 形式,也可以方便的转化库中的指定接口函数,示例代码如下:

var promisify = require("promisify-node");
var db = promisify("dbHelper");  //express下的回调形式封装库
...
var rows = yield db.getById('tableName', {id:1});
  yield this.render('index', {
    title: rows[0].fieldName
  });
...

实现方法三(thunkify)

使用 thunkify 也能够完成封装,thunkify-wrap 是一个增强版的 thunkify。不过看说明,这种方法在未来的发展中可能会被淘汰,大概的使用方法如下:

var genify = require('thunkify-wrap').genify;
var db = genify("dbHelper");   //express下的回调形式封装库
...
var rows = yield db.getById('tableName', {id:1});
  yield this.render('index', {
    title: rows[0].fieldName
  });
...

实现方法四(直接方法)

直接改造原来 express 下的回调方式代码为 Promise 形式,代码及说明如下:

dbHelper.js

var options = { /* 数据库连接字串 */ };

var mysql = require('mysql');
var pool = mysql.createPool(options);

//原有非接口代码,对mysql的封装,执行sql语句
function execQuery(sql, values, callback) {
  var errinfo;
  pool.getConnection(function(err, connection) {
    if (err) {
      errinfo = 'DB-获取数据库连接异常!';
      throw errinfo;
    } else {
      var querys = connection.query(sql, values, function(err, rows) {
        release(connection);
        if (err) {
          errinfo = 'DB-SQL语句执行错误:' + err;
          callback(err);
        } else {
          callback(null,rows);    //注意:第一个参数必须为null
        }
      });
    }
  });
}

function release(connection) {
  try {
    connection.release(function(error) {
      if (error) {
        console.log('DB-关闭数据库连接异常!');
      }
    });
  } catch (err) {}
}
//对外接口代码,包装成返回Promise函数的形式
exports.getById = function(tablename, id){
  return new Promise(function(resolve, reject){
    var values = {id:id};
    var sql = 'select * from ?? where ?';
    execQuery(sql,[tablename, values], function(err, rows){
      if(err){
        reject(err);
      }else{
        resolve(rows);
      }
    })
  });
}

routes/index.js

var db = require("../dbHelper");
...
var rows = yield db.getById('tableName', {id:1});
  yield this.render('index', {
    title: rows[0].fieldName
  });
...

代码

示例部分代码取自该项目:

https://github.com/zhoutk/koadmin.git

小结

koa 框架以 co 库为核心组织,很好的用 generator 来解决了回调函数问题。进行 Promise 接口形式包装的时候,要注意:回调函数要完全符合其要求的形式:

function(err, rows){
  if(err){
    reject(err);
  }else{
    resolve(rows);
  }
})

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

关于作者

JSmiles

生命进入颠沛而奔忙的本质状态,并将以不断告别和相遇的陈旧方式继续下去。

0 文章
0 评论
84961 人气
更多

推荐作者

已经忘了多久

文章 0 评论 0

15867725375

文章 0 评论 0

LonelySnow

文章 0 评论 0

走过海棠暮

文章 0 评论 0

轻许诺言

文章 0 评论 0

信馬由缰

文章 0 评论 0

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文