zoukankan      html  css  js  c++  java
  • sequelize之通过options生成sql语句

    前言

    在node.js web框架中使用sequelize来作为ORM是十分方便的。但是,有的时候我们需要用到子查询语句,使用sequelize无法完成需求。这时候,

    如果你的查询语句不是很复杂,可以使用sequelize提供的query()方法直接执行生成的sql语句。

    如果你的查询语句很复杂,但是子表查询结果数据不是很多,你可以先把子表查询结果获取到,在后端代码中进行数据处理,完成其它操作。

    如果你的查询语句很复杂,并且子表查询结果数据非常多,不可能在代码中完成数据处理,简单的可以执行两次,第一次查询字表数据,获取到查询的sql语句,拼接好子查询语句后再查询一次即可。

    由于sequelize只有执行查询后才可以在logging的回调函数中获取到生成的sql语句,这样就会多执行一次无用的数据库查询,下边写一个不执行查询获取sql语句的方法。

    实例

    • 以nodejs为例
    • 根据options获取sql语句
    const Utils = require('sequelize/lib/utils');
    /**
    * @parms model 当前表的模型实例
    * @options {object} 查询参数
    */
    module.exports = function genSqlString(model, options) {
        return (function (options) {
            const tableNames = {};
            tableNames[this.getTableName(options)] = true;
            options = Utils.cloneDeep(options);
            options = Object.assign({}, options, {
                hooks: true,
                rejectOnEmpty: true,
                type: 'SELECT',
                model: this,
                tableNames: Object.keys(tableNames)
            });
            options.originalAttributes = this._injectDependentVirtualAttributes(options.attributes);
    
            if (options.include) {
                options.hasJoin = true;
    
                this._validateIncludedElements(options, tableNames);
    
                if (
                    options.attributes
                    && !options.raw
                    && this.primaryKeyAttribute
                    && !options.attributes.includes(this.primaryKeyAttribute)
                    && (!options.group || !options.hasSingleAssociation || options.hasMultiAssociation)
                ) {
                    options.attributes = [this.primaryKeyAttribute].concat(options.attributes);
                }
            }
    
            if (!options.attributes) {
                options.attributes = Object.keys(this.rawAttributes);
                options.originalAttributes = this._injectDependentVirtualAttributes(options.attributes);
            }
    
            this.options.whereCollection = options.where || null;
    
            Utils.mapFinderOptions(options, this);
    
            options = this._paranoidClause(this, options);
            return this.QueryGenerator.selectQuery(this.getTableName(options), options, this);
        }).bind(model)(options);
    };
    
    • 补充一个执行后获取sql语句的实例
    let sql = '';
    options.logging = function (str) {
        sql = str.substring(20, str.length-1); // 截取其中的sql语句
    };
    await models.OrderBasic.findAll(options); // options为查询时存入的参数
    

    总结

    1. 获取sql语句的方法实际上是将源码中生成sql语句的部分提取出来了

    2. 目前还没有遇到sql解析错误,等遇到了再来更新

  • 相关阅读:
    webpack学习(一)—— 入门
    AMD 规范
    CommonJS 规范
    webpack 故障处理
    webpack 开发环境
    webpack 插件
    webpack 配置文件
    webpack 使用
    webpack Loader
    webpack常用的插件安装命令
  • 原文地址:https://www.cnblogs.com/xpengp/p/13164311.html
Copyright © 2011-2022 走看看