<commit_before>var should = require('should');
var path = require('path');
var helper = require('../support/spec_helper');
var sinon = require('sinon');
var common = require('../common');

describe("db.driver", function () {
  var db = null;

  before(function (done) {
    helper.connect(function (connection) {
      db = connection;

      var Log = db.define('log', {
        what: { type: 'text' },
        when: { type: 'date', time: true },
        who: { type: 'text' }
      });

      helper.dropSync(Log, function (err) {
        if (err) return done(err);

        Log.create([
          { what: "password reset", when: new Date('2013/04/07 12:33:05'), who: "jane" },
          { what: "user login", when: new Date('2013/04/07 13:01:44'), who: "jane" },
          { what: "user logout", when: new Date('2013/05/12 04:09:31'), who: "john" }
        ], done);
      });
    });
  });

  after(function () {
    return db.close();
  });

  it("should be available", function () {
    should.exist(db.driver);
  });

  if (common.protocol() === "mongodb") return;

  describe("query", function () {
    it("should be available", function () {
      should.exist(db.driver.query);
    });

    describe('#execQueryAsync', function () {
      it('should execute sql queries', function () {
        return db.driver.execQueryAsync('SELECT id FROM log')
          .then(function (data) {
            should(JSON.stringify(data) === JSON.stringify([{ id: 1 }, { id: 2 }, { id: 3 }]));
          })
      });

      it("should escape sql queries", function () {
        var query = "SELECT log.?? FROM log WHERE log.?? LIKE ? AND log.?? > ?";
        var args = ['what', 'who', 'jane', 'when', new Date('2013/04/07 12:40:00')];
        return db.driver.execQueryAsync(query, args)
          .then(function (data) {
            should(JSON.stringify(data) === JSON.stringify([{ "what": "user login" }]));
          });
      });
    });

    describe('#eagerQuery', function () {
      if (common.protocol() === "redshift") return;
      var fixture = {
        association: {
          model: {
            table: 'dog'
          },
          field: {
            dog_id: {
              type: 'serial',
              key: true,
              required: false,
              klass: 'primary',
              enumerable: true,
              mapsTo: 'dog_id',
              name: 'dog_id'
            }
          },
          mergeAssocId: {
            family_id: {
              type: 'integer',
              required: true,
              klass: 'primary',
              enumerable: true,
              mapsTo: 'family_id',
              name: 'family_id'
            }
          },
          mergeTable: 'dog_family',
        },
        opts: {
          only: ['name', 'id'],
          keys: ['id'],
        },
        expectedQuery: {
          postgres: 'SELECT "t1"."name", "t1"."id", "t2"."dog_id" AS "$p" FROM "dog" "t1" JOIN "dog_family" "t2" ON "t2"."family_id" = "t1"."id" WHERE "t2"."dog_id" IN (1, 5)',
          mysql: 'SELECT `t1`.`name`, `t1`.`id`, `t2`.`dog_id` AS `$p` FROM `dog` `t1` JOIN `dog_family` `t2` ON `t2`.`family_id` = `t1`.`id` WHERE `t2`.`dog_id` IN (1, 5)',
          sqlite: 'SELECT `t1`.`name`, `t1`.`id`, `t2`.`dog_id` AS `$p` FROM `dog` `t1` JOIN `dog_family` `t2` ON `t2`.`family_id` = `t1`.`id` WHERE `t2`.`dog_id` IN (1, 5)'
        }
      };

      describe('cb', function () {
        it('should build correct query', function (done) {
          var execSimpleQueryStub = sinon.stub(db.driver, 'execSimpleQuery')
            .callsFake(function (q, cb) {
              cb();
            });

          db.driver.eagerQuery(fixture.association, fixture.opts, [1, 5], function (err, data) {
            if (err) {
              execSimpleQueryStub.restore();
              done(err);
            }
            should.equal(execSimpleQueryStub.calledOnce, true);
            should.equal(execSimpleQueryStub.lastCall.args[0], fixture.expectedQuery[common.protocol()]);
            execSimpleQueryStub.restore();
            done();
          });
        });
      });

      describe('async', function () {
        it('should build correct query', function () {
          var execSimpleQueryStub = sinon.stub(db.driver, 'execSimpleQuery')
            .callsFake(function (q, cb) {
              cb();
            });
          return db.driver.eagerQueryAsync(fixture.association, fixture.opts, [1, 5])
            .then(function () {
              should.equal(execSimpleQueryStub.calledOnce, true);
              should.equal(execSimpleQueryStub.lastCall.args[0], fixture.expectedQuery[common.protocol()]);
              execSimpleQueryStub.restore();
            })
            .catch(function () {
              execSimpleQueryStub.restore();
            });
        });
      });
    });

    describe("#generateQuery", function () {
      it("should return interpolated & escaped SQL", function () {
        var expected = "expectation missing; unknown protocol";

        switch (common.protocol()) {
          case 'mysql':
          case 'sqlite':
            expected = "UPDATE `animals` SET `name` = 'cat' WHERE `id` = 9"
            break;
          case 'postgres':
            expected = 'UPDATE "animals" SET "name" = \'cat\' WHERE "id" = 9'
            break;
        }

        should.equal(
          db.driver.generateQuery("UPDATE ?? SET ?? = ? WHERE ?? = ?", ['animals', 'name', 'cat', 'id', 9]),
          expected,
        );
      });
    });

    describe("#execQuery", function () {
      it("should execute sql queries", function (done) {
        db.driver.execQuery("SELECT id FROM log", function (err, data) {
          should.not.exist(err);
<commit_msg>Fix redshift test failure<commit_after>var should = require('should');
var path = require('path');
var helper = require('../support/spec_helper');
var sinon = require('sinon');
var common = require('../common');

describe("db.driver", function () {
  var db = null;

  before(function (done) {
    helper.connect(function (connection) {
      db = connection;

      var Log = db.define('log', {
        what: { type: 'text' },
        when: { type: 'date', time: true },
        who: { type: 'text' }
      });

      helper.dropSync(Log, function (err) {
        if (err) return done(err);

        Log.create([
          { what: "password reset", when: new Date('2013/04/07 12:33:05'), who: "jane" },
          { what: "user login", when: new Date('2013/04/07 13:01:44'), who: "jane" },
          { what: "user logout", when: new Date('2013/05/12 04:09:31'), who: "john" }
        ], done);
      });
    });
  });

  after(function () {
    return db.close();
  });

  it("should be available", function () {
    should.exist(db.driver);
  });

  if (common.protocol() === "mongodb") return;

  describe("query", function () {
    it("should be available", function () {
      should.exist(db.driver.query);
    });

    describe('#execQueryAsync', function () {
      it('should execute sql queries', function () {
        return db.driver.execQueryAsync('SELECT id FROM log')
          .then(function (data) {
            should(JSON.stringify(data) === JSON.stringify([{ id: 1 }, { id: 2 }, { id: 3 }]));
          })
      });

      it("should escape sql queries", function () {
        var query = "SELECT log.?? FROM log WHERE log.?? LIKE ? AND log.?? > ?";
        var args = ['what', 'who', 'jane', 'when', new Date('2013/04/07 12:40:00')];
        return db.driver.execQueryAsync(query, args)
          .then(function (data) {
            should(JSON.stringify(data) === JSON.stringify([{ "what": "user login" }]));
          });
      });
    });

    describe('#eagerQuery', function () {
      if (common.protocol() === "redshift") return;
      var fixture = {
        association: {
          model: {
            table: 'dog'
          },
          field: {
            dog_id: {
              type: 'serial',
              key: true,
              required: false,
              klass: 'primary',
              enumerable: true,
              mapsTo: 'dog_id',
              name: 'dog_id'
            }
          },
          mergeAssocId: {
            family_id: {
              type: 'integer',
              required: true,
              klass: 'primary',
              enumerable: true,
              mapsTo: 'family_id',
              name: 'family_id'
            }
          },
          mergeTable: 'dog_family',
        },
        opts: {
          only: ['name', 'id'],
          keys: ['id'],
        },
        expectedQuery: {
          postgres: 'SELECT "t1"."name", "t1"."id", "t2"."dog_id" AS "$p" FROM "dog" "t1" JOIN "dog_family" "t2" ON "t2"."family_id" = "t1"."id" WHERE "t2"."dog_id" IN (1, 5)',
          mysql: 'SELECT `t1`.`name`, `t1`.`id`, `t2`.`dog_id` AS `$p` FROM `dog` `t1` JOIN `dog_family` `t2` ON `t2`.`family_id` = `t1`.`id` WHERE `t2`.`dog_id` IN (1, 5)',
          sqlite: 'SELECT `t1`.`name`, `t1`.`id`, `t2`.`dog_id` AS `$p` FROM `dog` `t1` JOIN `dog_family` `t2` ON `t2`.`family_id` = `t1`.`id` WHERE `t2`.`dog_id` IN (1, 5)'
        }
      };

      describe('cb', function () {
        it('should build correct query', function (done) {
          var execSimpleQueryStub = sinon.stub(db.driver, 'execSimpleQuery')
            .callsFake(function (q, cb) {
              cb();
            });

          db.driver.eagerQuery(fixture.association, fixture.opts, [1, 5], function (err, data) {
            if (err) {
              execSimpleQueryStub.restore();
              done(err);
            }
            should.equal(execSimpleQueryStub.calledOnce, true);
            should.equal(execSimpleQueryStub.lastCall.args[0], fixture.expectedQuery[common.protocol()]);
            execSimpleQueryStub.restore();
            done();
          });
        });
      });

      describe('async', function () {
        it('should build correct query', function () {
          var execSimpleQueryStub = sinon.stub(db.driver, 'execSimpleQuery')
            .callsFake(function (q, cb) {
              cb();
            });
          return db.driver.eagerQueryAsync(fixture.association, fixture.opts, [1, 5])
            .then(function () {
              should.equal(execSimpleQueryStub.calledOnce, true);
              should.equal(execSimpleQueryStub.lastCall.args[0], fixture.expectedQuery[common.protocol()]);
              execSimpleQueryStub.restore();
            })
            .catch(function () {
              execSimpleQueryStub.restore();
            });
        });
      });
    });

    describe("#generateQuery", function () {
      it("should return interpolated & escaped SQL", function () {
        var expected = "expectation missing; unknown protocol " + common.protocol();

        switch (common.protocol()) {
          case 'mysql':
          case 'sqlite':
            expected = "UPDATE `animals` SET `name` = 'cat' WHERE `id` = 9"
            break;
          case 'postgres':
          case 'redshift':
            expected = 'UPDATE "animals" SET "name" = \'cat\' WHERE "id" = 9'
            break;
        }

        should.equal(
          db.driver.generateQuery("UPDATE ?? SET ?? = ? WHERE ?? = ?", ['animals', 'name', 'cat', 'id', 9]),
          expected,
        );
      });
    });

    describe("#execQuery", function () {
      it("should execute sql queries", function (done) {
        db.driver.execQuery("SELECT id FROM log", function (err, data) {
          should.not.exist(err);

{'fraction_non_alphanumeric': 0.17147575178167912, 'fraction_numerical': 0.01703459064835738, 'mean_word_length': 1.9220416455053326, 'pattern_counts': {'":': 2, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2189666', 'n_tokens_mistral': 3575, 'n_tokens_neox': 3439, 'n_words': 796}