美文网首页Nodejs全栈开发web前端开发大全
nodejs使用async/await同步操作mysql

nodejs使用async/await同步操作mysql

作者: 宇cccc | 来源:发表于2018-01-22 17:14 被阅读5652次

    注: 教程基于koa2 node.js版本需要>=7.6, 当然同样适用于express,因为async/await是JavaScript的ESnext的新特性

    Node.js的核心概念是非阻塞IO和异步编程。虽然这种机制给Node.js带来了巨大的优势和好处,但同时它也带来了许多问题和挑战,比如我们在做一些异步操作的时候,如果需要拿到异步操作返回的结果之后再进行下一步操作,通常需要通过一层层的异步回调,导致维护十分困难,代码可读性差,koa2天生就支持async特性,当然目前在express也可以使用。

    安装 mysql驱动

    mysql文档地址 当然在此之前你必须先安装并启动mysql
    npm install mysql --save

    创建mysql连接

    const mysql      = require('mysql')
    
    const connection = mysql.createConnection({
      host     : '127.0.0.1',   // 数据库地址
      user     : 'root',    // 数据库用户
      password : '123456'   // 数据库密码
      database : 'my_database'  // 选中数据库
    })
    
    // 连接数据库 这一步不是必须的 因为在query的时候会默认连接
    connection.connect((err) => {
        // 如果在这一步抛出错误 请检查数据库配置  比如权限 选中数据库是否存在等等..
        if (err) return console.log('数据库连接失败', err.message);
        console.log('数据库连接成功');
    })
    
    // 执行sql脚本对数据库进行读写 
    connection.query('SELECT * FROM my_table',  (error, results, fields) => {
      if (error) throw error
      // connected! 
    
      // 结束会话
      connection.release() 
    });
    
    

    注意:一个事件就有一个从开始到结束的过程,数据库会话操作执行完后,就需要关闭掉,以免占用连接资源。

    创建数据连接池

    一般情况下,我们不会按照上面的做法,因为一般操作数据库是很复杂的读写过程,不只是一个会话,如果直接用会话操作,就需要每次会话都要配置连接参数,所以这时候就需要连接池管理会话(如果使用MongoDB则无需担心这些问题mongo会管理自己的连接集合,或连接"池")

    const mysql = require('mysql')
    
    // 创建数据池
    const pool  = mysql.createPool({
      host     : '127.0.0.1',   // 数据库地址
      user     : 'root',    // 数据库用户
      password : '123456'   // 数据库密码
      database : 'my_database'  // 选中数据库
    })
    
    // 在数据池中进行会话操作
    pool.getConnection(function(err, connection) {
    
      connection.query('SELECT * FROM my_table',  (error, results, fields) => {
    
        // 结束会话
        connection.release();
    
        // 如果有错误就抛出
        if (error) throw error;
      })
    })
    

    封装mysql请求

    前面内容作为前置知识,由于mysql模块的操作都是异步操作,每次操作的结果都是在回调函数中执行,现在有了async/await,就可以用同步的写法去操作数据库
    对于async/await不熟悉的朋友请先查阅相关文档以了解用法,不过没熟悉也没关系,记住async/await 需要返回一个 Promise 对象就可以了.

    const mysql = require('mysql')
    const pool = mysql.createPool({
      host     :  '127.0.0.1',
      user     :  'root',
      password :  '123456',
      database :  'my_database'
    })
    
    // 接收一个sql语句 以及所需的values
    // 这里接收第二参数values的原因是可以使用mysql的占位符 '?'
    // 比如 query(`select * from my_database where id = ?`, [1])
    
    let query = function( sql, values ) {
      // 返回一个 Promise
      return new Promise(( resolve, reject ) => {
        pool.getConnection(function(err, connection) {
          if (err) {
            reject( err )
          } else {
            connection.query(sql, values, ( err, rows) => {
    
              if ( err ) {
                reject( err )
              } else {
                resolve( rows )
              }
              // 结束会话
              connection.release()
            })
          }
        })
      })
    }
    
    module.exports =  query
    

    简单的我们就封装好了,这个时候我们可以这么使用

    koa2

    router.post('/login', async (ctx) => {
        // 这里可以同步获取到rows
        let rows = await query('select * from im_user')
        ctx.body = {
            code: 0,
            msg: '请求成功',
            data: rows
        }
    })
    

    express

    router.post('/login', async (req, res) => {
        
        // 原来做法
        // query('select * from im_user', (err, rows) => {
        //     res.json({
        //         code: 0,
        //         msg: '请求成功',
        //         data: rows
        //     })
        // })
        
        // 现在
        const rows = await query('select * from im_user')
        res.json({
            code: 0,
            msg: '请求成功',
            data: rows
        })
        
    })
    

    当然 如果你觉得把sql语句散落在各个地方不太好,你可以统一管理.

    源码地址 koa-gachat

    相关文章

      网友评论

        本文标题:nodejs使用async/await同步操作mysql

        本文链接:https://www.haomeiwen.com/subject/kyzlaxtx.html