不要怂,就是干,撸起袖子干!

Commit 7e823676 by Sascha Depold

Merge branch 'mocha' of github.com:sequelize/sequelize into mocha

2 parents fa959096 cc5ffa4f
test: REPORTER ?= dot
@./node_modules/mocha/bin/mocha -c $(find ./test -name "*.test.js") TESTS = $(shell find ./test/* -name "*.test.js")
.PHONY: test sqlite:
@DIALECT=sqlite ./node_modules/mocha/bin/mocha \
--colors \
--reporter $(REPORTER) \
$(TESTS)
mysql:
@DIALECT=mysql ./node_modules/mocha/bin/mocha \
--colors \
--reporter $(REPORTER) \
$(TESTS)
.PHONY: sqlite mysql
\ No newline at end of file
...@@ -10,10 +10,11 @@ var chai = require('chai') ...@@ -10,10 +10,11 @@ var chai = require('chai')
chai.Assertion.includeStack = true chai.Assertion.includeStack = true
describe(Support.getTestDialectTeaser("Configuration"), function() { describe(Support.getTestDialectTeaser("Configuration"), function() {
/*describe('Connections problems should fail with a nice message', function() { describe.skip('Connections problems should fail with a nice message', function() {
it("when we don't have the correct server details", function(done) { it("when we don't have the correct server details", function(done) {
if (noDomains === true) { if (noDomains === true) {
console.log('WARNING: Configuration specs requires NodeJS version >= 0.8 for full compatibility') console.log('WARNING: Configuration specs requires NodeJS version >= 0.8 for full compatibility')
expect('').to.equal('') // Silence Buster!
done() done()
} else { } else {
var seq = new Sequelize(config[dialect].database, config[dialect].username, config[dialect].password, {storage: '/path/to/no/where/land', logging: false, host: '0.0.0.1', port: config[dialect].port, dialect: dialect}) var seq = new Sequelize(config[dialect].database, config[dialect].username, config[dialect].password, {storage: '/path/to/no/where/land', logging: false, host: '0.0.0.1', port: config[dialect].port, dialect: dialect})
...@@ -37,11 +38,11 @@ describe(Support.getTestDialectTeaser("Configuration"), function() { ...@@ -37,11 +38,11 @@ describe(Support.getTestDialectTeaser("Configuration"), function() {
it('when we don\'t have the correct login information', function(done) { it('when we don\'t have the correct login information', function(done) {
if (dialect !== "postgres" && dialect !== "postgres-native" && dialect !== "mysql") { if (dialect !== "postgres" && dialect !== "postgres-native" && dialect !== "mysql") {
console.log('This dialect doesn\'t support me :(') console.log('This dialect doesn\'t support me :(')
expect('').toEqual('') // Silence Buster expect('').to.equal('') // Silence Buster
return done() return done()
} else if (noDomains === true) { } else if (noDomains === true) {
console.log('WARNING: Configuration specs requires NodeJS version >= 0.8 for full compatibility') console.log('WARNING: Configuration specs requires NodeJS version >= 0.8 for full compatibility')
expect('').toEqual('') // Silence Buster! expect('').to.equal('') // Silence Buster!
return done() return done()
} else { } else {
var seq = new Sequelize(config[dialect].database, config[dialect].username, 'fakepass123', {logging: false, host: config[dialect].host, port: 1, dialect: dialect}) var seq = new Sequelize(config[dialect].database, config[dialect].username, 'fakepass123', {logging: false, host: config[dialect].host, port: 1, dialect: dialect})
...@@ -67,7 +68,7 @@ describe(Support.getTestDialectTeaser("Configuration"), function() { ...@@ -67,7 +68,7 @@ describe(Support.getTestDialectTeaser("Configuration"), function() {
}).to.throw('The dialect undefined is not supported.') }).to.throw('The dialect undefined is not supported.')
done() done()
}) })
})*/ })
describe('Instantiation with a URL string', function() { describe('Instantiation with a URL string', function() {
it('should accept username, password, host, port, and database', function() { it('should accept username, password, host, port, and database', function() {
...@@ -84,42 +85,46 @@ describe(Support.getTestDialectTeaser("Configuration"), function() { ...@@ -84,42 +85,46 @@ describe(Support.getTestDialectTeaser("Configuration"), function() {
expect(config.port).to.equal('9821') expect(config.port).to.equal('9821')
}) })
it('should work with no authentication options', function() { it('should work with no authentication options', function(done) {
var sequelize = new Sequelize('mysql://example.com:9821/dbname') var sequelize = new Sequelize('mysql://example.com:9821/dbname')
var config = sequelize.config var config = sequelize.config
expect(config.username).to.equal(undefined) expect(config.username).to.not.be.ok
expect(config.password).to.equal(null) expect(config.password).to.be.null
done()
}) })
it('should use the default port when no other is specified', function() { it('should use the default port when no other is specified', function(done) {
var sequelize = new Sequelize('mysql://example.com/dbname') var sequelize = new Sequelize('mysql://example.com/dbname')
var config = sequelize.config var config = sequelize.config
// The default port should be set // The default port should be set
expect(config.port).to.equal(3306) expect(config.port).to.equal(3306)
done()
}) })
}) })
describe('Intantiation with arguments', function() { describe('Intantiation with arguments', function() {
it('should accept two parameters (database, username)', function() { it('should accept two parameters (database, username)', function(done) {
var sequelize = new Sequelize('dbname', 'root') var sequelize = new Sequelize('dbname', 'root')
var config = sequelize.config var config = sequelize.config
expect(config.database).to.equal('dbname') expect(config.database).to.equal('dbname')
expect(config.username).to.equal('root') expect(config.username).to.equal('root')
done()
}) })
it('should accept three parameters (database, username, password)', function() { it('should accept three parameters (database, username, password)', function(done) {
var sequelize = new Sequelize('dbname', 'root', 'pass') var sequelize = new Sequelize('dbname', 'root', 'pass')
var config = sequelize.config var config = sequelize.config
expect(config.database).to.equal('dbname') expect(config.database).to.equal('dbname')
expect(config.username).to.equal('root') expect(config.username).to.equal('root')
expect(config.password).to.equal('pass') expect(config.password).to.equal('pass')
done()
}) })
it('should accept four parameters (database, username, password, options)', function() { it('should accept four parameters (database, username, password, options)', function(done) {
var sequelize = new Sequelize('dbname', 'root', 'pass', { port: 999 }) var sequelize = new Sequelize('dbname', 'root', 'pass', { port: 999 })
var config = sequelize.config var config = sequelize.config
...@@ -127,6 +132,7 @@ describe(Support.getTestDialectTeaser("Configuration"), function() { ...@@ -127,6 +132,7 @@ describe(Support.getTestDialectTeaser("Configuration"), function() {
expect(config.username).to.equal('root') expect(config.username).to.equal('root')
expect(config.password).to.equal('pass') expect(config.password).to.equal('pass')
expect(config.port).to.equal(999) expect(config.port).to.equal(999)
done()
}) })
}) })
}) })
...@@ -114,16 +114,16 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -114,16 +114,16 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
describe('increment', function () { describe('increment', function () {
beforeEach(function(done) { beforeEach(function(done) {
this.User.create({ id: 1, aNumber: 0, bNumber: 0 }).done(function(){ this.User.create({ id: 1, aNumber: 0, bNumber: 0 }).complete(function(){
done() done()
}) })
}) })
it('with array', function(done) { it('with array', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.increment(['aNumber'], 2).done(function() { user1.increment(['aNumber'], 2).complete(function() {
self.User.find(1).done(function(err, user3) { self.User.find(1).complete(function(err, user3) {
expect(user3.aNumber).to.be.equal(2) expect(user3.aNumber).to.be.equal(2)
done() done()
}) })
...@@ -133,9 +133,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -133,9 +133,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('with single field', function(done) { it('with single field', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.increment('aNumber', 2).done(function() { user1.increment('aNumber', 2).complete(function() {
self.User.find(1).done(function(err, user3) { self.User.find(1).complete(function(err, user3) {
expect(user3.aNumber).to.be.equal(2) expect(user3.aNumber).to.be.equal(2)
done() done()
}) })
...@@ -145,14 +145,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -145,14 +145,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('should still work right with other concurrent updates', function(done) { it('should still work right with other concurrent updates', function(done) {
var self = this var self = this
this.User.find(1).done(function (err, user1) { this.User.find(1).complete(function (err, user1) {
// Select the user again (simulating a concurrent query) // Select the user again (simulating a concurrent query)
self.User.find(1).done(function (err, user2) { self.User.find(1).complete(function (err, user2) {
user2.updateAttributes({ user2.updateAttributes({
aNumber: user2.aNumber + 1 aNumber: user2.aNumber + 1
}).done(function () { }).complete(function () {
user1.increment(['aNumber'], 2).done(function() { user1.increment(['aNumber'], 2).complete(function() {
self.User.find(1).done(function(err, user5) { self.User.find(1).complete(function(err, user5) {
expect(user5.aNumber).to.be.equal(3) expect(user5.aNumber).to.be.equal(3)
done() done()
}) })
...@@ -164,25 +164,25 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -164,25 +164,25 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('should still work right with other concurrent increments', function(done) { it('should still work right with other concurrent increments', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
var _done = _.after(3, function() { var _done = _.after(3, function() {
self.User.find(1).done(function(err, user2) { self.User.find(1).complete(function(err, user2) {
expect(user2.aNumber).to.equal(6) expect(user2.aNumber).to.equal(6)
done() done()
}) })
}) })
user1.increment(['aNumber'], 2).done(_done) user1.increment(['aNumber'], 2).complete(_done)
user1.increment(['aNumber'], 2).done(_done) user1.increment(['aNumber'], 2).complete(_done)
user1.increment(['aNumber'], 2).done(_done) user1.increment(['aNumber'], 2).complete(_done)
}) })
}) })
it('with key value pair', function(done) { it('with key value pair', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.increment({ 'aNumber': 1, 'bNumber': 2}).done(function() { user1.increment({ 'aNumber': 1, 'bNumber': 2}).success(function() {
self.User.find(1).done(function (err, user3) { self.User.find(1).complete(function (err, user3) {
expect(user3.aNumber).to.be.equal(1) expect(user3.aNumber).to.be.equal(1)
expect(user3.bNumber).to.be.equal(2) expect(user3.bNumber).to.be.equal(2)
done() done()
...@@ -194,14 +194,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -194,14 +194,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
describe('decrement', function () { describe('decrement', function () {
beforeEach(function(done) { beforeEach(function(done) {
this.User.create({ id: 1, aNumber: 0, bNumber: 0 }).done(done) this.User.create({ id: 1, aNumber: 0, bNumber: 0 }).complete(done)
}) })
it('with array', function(done) { it('with array', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.decrement(['aNumber'], 2).done(function() { user1.decrement(['aNumber'], 2).complete(function() {
self.User.find(1).done(function(err, user3) { self.User.find(1).complete(function(err, user3) {
expect(user3.aNumber).to.be.equal(-2) expect(user3.aNumber).to.be.equal(-2)
done() done()
}) })
...@@ -211,9 +211,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -211,9 +211,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('with single field', function(done) { it('with single field', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.decrement('aNumber', 2).done(function() { user1.decrement('aNumber', 2).complete(function() {
self.User.find(1).done(function(err, user3) { self.User.find(1).complete(function(err, user3) {
expect(user3.aNumber).to.be.equal(-2) expect(user3.aNumber).to.be.equal(-2)
done() done()
}) })
...@@ -223,14 +223,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -223,14 +223,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('should still work right with other concurrent updates', function(done) { it('should still work right with other concurrent updates', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
// Select the user again (simulating a concurrent query) // Select the user again (simulating a concurrent query)
self.User.find(1).done(function(err, user2) { self.User.find(1).complete(function(err, user2) {
user2.updateAttributes({ user2.updateAttributes({
aNumber: user2.aNumber + 1 aNumber: user2.aNumber + 1
}).done(function () { }).complete(function () {
user1.decrement(['aNumber'], 2).done(function() { user1.decrement(['aNumber'], 2).complete(function() {
self.User.find(1).done(function(err, user5) { self.User.find(1).complete(function(err, user5) {
expect(user5.aNumber).to.be.equal(-1) expect(user5.aNumber).to.be.equal(-1)
done() done()
}) })
...@@ -242,25 +242,25 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -242,25 +242,25 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it('should still work right with other concurrent increments', function(done) { it('should still work right with other concurrent increments', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
var _done = _.after(3, function() { var _done = _.after(3, function() {
self.User.find(1).done(function (err, user2) { self.User.find(1).complete(function (err, user2) {
expect(user2.aNumber).to.equal(-6) expect(user2.aNumber).to.equal(-6)
done() done()
}) })
}) })
user1.decrement(['aNumber'], 2).done(_done) user1.decrement(['aNumber'], 2).complete(_done)
user1.decrement(['aNumber'], 2).done(_done) user1.decrement(['aNumber'], 2).complete(_done)
user1.decrement(['aNumber'], 2).done(_done) user1.decrement(['aNumber'], 2).complete(_done)
}) })
}) })
it('with key value pair', function(done) { it('with key value pair', function(done) {
var self = this var self = this
this.User.find(1).done(function(err, user1) { this.User.find(1).complete(function(err, user1) {
user1.decrement({ 'aNumber': 1, 'bNumber': 2}).done(function() { user1.decrement({ 'aNumber': 1, 'bNumber': 2}).complete(function() {
self.User.find(1).done(function(err, user3) { self.User.find(1).complete(function(err, user3) {
expect(user3.aNumber).to.be.equal(-1) expect(user3.aNumber).to.be.equal(-1)
expect(user3.bNumber).to.be.equal(-2) expect(user3.bNumber).to.be.equal(-2)
done() done()
...@@ -272,9 +272,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -272,9 +272,9 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
describe('reload', function () { describe('reload', function () {
it("should return a reference to the same DAO instead of creating a new one", function(done) { it("should return a reference to the same DAO instead of creating a new one", function(done) {
this.User.create({ username: 'John Doe' }).done(function(err, originalUser) { this.User.create({ username: 'John Doe' }).complete(function(err, originalUser) {
originalUser.updateAttributes({ username: 'Doe John' }).done(function() { originalUser.updateAttributes({ username: 'Doe John' }).complete(function() {
originalUser.reload().done(function (err, updatedUser) { originalUser.reload().complete(function (err, updatedUser) {
expect(originalUser === updatedUser).to.be.true expect(originalUser === updatedUser).to.be.true
done() done()
}) })
...@@ -284,13 +284,13 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -284,13 +284,13 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
it("should update the values on all references to the DAO", function(done) { it("should update the values on all references to the DAO", function(done) {
var self = this var self = this
this.User.create({ username: 'John Doe' }).done(function(err, originalUser) { this.User.create({ username: 'John Doe' }).complete(function(err, originalUser) {
self.User.find(originalUser.id).done(function(err, updater) { self.User.find(originalUser.id).complete(function(err, updater) {
updater.updateAttributes({ username: 'Doe John' }).done(function() { updater.updateAttributes({ username: 'Doe John' }).complete(function() {
// We used a different reference when calling updateAttributes, so originalUser is now out of sync // We used a different reference when calling updateAttributes, so originalUser is now out of sync
expect(originalUser.username).to.equal('John Doe') expect(originalUser.username).to.equal('John Doe')
originalUser.reload().done(function(err, updatedUser) { originalUser.reload().complete(function(err, updatedUser) {
expect(originalUser.username).to.equal('Doe John') expect(originalUser.username).to.equal('Doe John')
expect(updatedUser.username).to.equal('Doe John') expect(updatedUser.username).to.equal('Doe John')
done() done()
...@@ -304,14 +304,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -304,14 +304,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
var self = this var self = this
this.timeout = 2000 this.timeout = 2000
this.User.create({ username: 'John Doe' }).done(function(err, originalUser) { this.User.create({ username: 'John Doe' }).complete(function(err, originalUser) {
var originallyUpdatedAt = originalUser.updatedAt var originallyUpdatedAt = originalUser.updatedAt
// Wait for a second, so updatedAt will actually be different // Wait for a second, so updatedAt will actually be different
setTimeout(function () { setTimeout(function () {
self.User.find(originalUser.id).done(function(err, updater) { self.User.find(originalUser.id).complete(function(err, updater) {
updater.updateAttributes({ username: 'Doe John' }).done(function () { updater.updateAttributes({ username: 'Doe John' }).complete(function () {
originalUser.reload().done(function(err, updatedUser) { originalUser.reload().complete(function(err, updatedUser) {
expect(originalUser.updatedAt).to.be.above(originallyUpdatedAt) expect(originalUser.updatedAt).to.be.above(originallyUpdatedAt)
expect(updatedUser.updatedAt).to.be.above(originallyUpdatedAt) expect(updatedUser.updatedAt).to.be.above(originallyUpdatedAt)
done() done()
...@@ -453,10 +453,10 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -453,10 +453,10 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
}) })
User.all().success(function(users) { User.all().success(function(users) {
expect(users.length).to.equal(0) expect(users).to.have.length(0)
user.save().success(function(){ user.save().success(function(){
User.all().success(function(users) { User.all().success(function(users) {
expect(users.length).to.equal(1) expect(users).to.have.length(1)
expect(users[0].username).to.equal(username) expect(users[0].username).to.equal(username)
expect(users[0].touchedAt).to.be.instanceof(Date) expect(users[0].touchedAt).to.be.instanceof(Date)
expect(users[0].touchedAt).to.equalDate(new Date(1984, 8, 23)) expect(users[0].touchedAt).to.equalDate(new Date(1984, 8, 23))
...@@ -466,14 +466,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -466,14 +466,14 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
}) })
}) })
it("updates the timestamps", function() { it("updates the timestamps", function(done) {
var now = Date.now() var now = Date.now()
, user = null , user = null
, updatedAt = null , updatedAt = null
, User = this.User , User = this.User
// timeout is needed, in order to check the update of the timestamp // timeout is needed, in order to check the update of the timestamp
var build = function() { var build = function(callback) {
user = User.build({ username: 'user' }) user = User.build({ username: 'user' })
updatedAt = user.updatedAt updatedAt = user.updatedAt
expect(updatedAt.getTime()).to.be.above(now) expect(updatedAt.getTime()).to.be.above(now)
...@@ -481,11 +481,17 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -481,11 +481,17 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
setTimeout(function() { setTimeout(function() {
user.save().success(function() { user.save().success(function() {
expect(updatedAt.getTime()).to.be.below(user.updatedAt.getTime()) expect(updatedAt.getTime()).to.be.below(user.updatedAt.getTime())
callback()
}) })
}, 1000) }, 1000)
} }
setTimeout(build, 1000) // closures are fun :)
setTimeout(function() {
build(function() {
done()
})
}, 1000)
}) })
describe('without timestamps option', function() { describe('without timestamps option', function() {
...@@ -1046,9 +1052,8 @@ describe(Support.getTestDialectTeaser("DAO"), function () { ...@@ -1046,9 +1052,8 @@ describe(Support.getTestDialectTeaser("DAO"), function () {
expect(download.startedAt instanceof Date).to.be.true expect(download.startedAt instanceof Date).to.be.true
expect(download.canceledAt instanceof Date).to.be.true expect(download.canceledAt instanceof Date).to.be.true
expect(download.finishedAt).to.not.be.ok expect(download.finishedAt).to.not.be.ok
done()
}) })
done()
}) })
}) })
}) })
......
...@@ -2,6 +2,7 @@ var chai = require('chai') ...@@ -2,6 +2,7 @@ var chai = require('chai')
, expect = chai.expect , expect = chai.expect
, Sequelize = require(__dirname + '/../index') , Sequelize = require(__dirname + '/../index')
, Support = require(__dirname + '/support') , Support = require(__dirname + '/support')
, config = require(__dirname + '/config/config')
chai.Assertion.includeStack = true chai.Assertion.includeStack = true
...@@ -203,7 +204,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -203,7 +204,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
validations[validator].msg = message validations[validator].msg = message
var UserFail = this.sequelize.define('User' + Math.random(), { var UserFail = this.sequelize.define('User' + config.rand(), {
name: { name: {
type: Sequelize.STRING, type: Sequelize.STRING,
validate: validations validate: validations
...@@ -222,6 +223,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -222,6 +223,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
//////////////////////////// ////////////////////////////
// test the success cases // // test the success cases //
//////////////////////////// ////////////////////////////
for (var j = 0; j < validatorDetails.pass.length; j++) { for (var j = 0; j < validatorDetails.pass.length; j++) {
var succeedingValue = validatorDetails.pass[j] var succeedingValue = validatorDetails.pass[j]
...@@ -236,7 +238,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -236,7 +238,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
validations[validator].msg = validator + "(" + succeedingValue + ")" validations[validator].msg = validator + "(" + succeedingValue + ")"
var UserSuccess = this.sequelize.define('User' + Math.random(), { var UserSuccess = this.sequelize.define('User' + config.rand(), {
name: { name: {
type: Sequelize.STRING, type: Sequelize.STRING,
validate: validations validate: validations
...@@ -252,7 +254,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -252,7 +254,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
} }
it('correctly validates using custom validation methods', function(done) { it('correctly validates using custom validation methods', function(done) {
var User = this.sequelize.define('User' + Math.random(), { var User = this.sequelize.define('User' + config.rand(), {
name: { name: {
type: Sequelize.STRING, type: Sequelize.STRING,
validate: { validate: {
...@@ -278,7 +280,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -278,7 +280,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
}) })
it('skips other validations if allowNull is true and the value is null', function(done) { it('skips other validations if allowNull is true and the value is null', function(done) {
var User = this.sequelize.define('User' + Math.random(), { var User = this.sequelize.define('User' + config.rand(), {
age: { age: {
type: Sequelize.INTEGER, type: Sequelize.INTEGER,
allowNull: true, allowNull: true,
...@@ -304,7 +306,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() { ...@@ -304,7 +306,7 @@ describe(Support.getTestDialectTeaser("DaoValidator"), function() {
}) })
it('validates a model with custom model-wide validation methods', function(done) { it('validates a model with custom model-wide validation methods', function(done) {
var Foo = this.sequelize.define('Foo' + Math.random(), { var Foo = this.sequelize.define('Foo' + config.rand(), {
field1: { field1: {
type: Sequelize.INTEGER, type: Sequelize.INTEGER,
allowNull: true allowNull: true
......
/* jshint camelcase: false */
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, sinon = require('sinon')
, CustomEventEmitter = require("../../lib/emitters/custom-event-emitter")
chai.Assertion.includeStack = true
describe(Support.getTestDialectTeaser("CustomEventEmitter"), function () {
describe("proxy", function () {
it("should correctly work with success listeners", function(done) {
var emitter = new CustomEventEmitter()
, proxy = new CustomEventEmitter()
, success = sinon.spy()
emitter.success(success)
proxy.success(function () {
process.nextTick(function () {
expect(success.called).to.be.true
done()
})
})
proxy.proxy(emitter)
proxy.emit('success')
})
it("should correctly work with error listeners", function(done) {
var emitter = new CustomEventEmitter()
, proxy = new CustomEventEmitter()
, error = sinon.spy()
emitter.error(error)
proxy.error(function() {
process.nextTick(function() {
expect(error.called).to.be.true
done()
})
})
proxy.proxy(emitter)
proxy.emit('error')
})
it("should correctly work with complete/done listeners", function(done) {
var emitter = new CustomEventEmitter()
, proxy = new CustomEventEmitter()
, complete = sinon.spy()
emitter.complete(complete)
proxy.complete(function() {
process.nextTick(function() {
expect(complete.called).to.be.true
done()
})
})
proxy.proxy(emitter)
proxy.emit('success')
})
})
})
...@@ -6,17 +6,17 @@ var chai = require('chai') ...@@ -6,17 +6,17 @@ var chai = require('chai')
chai.Assertion.includeStack = true chai.Assertion.includeStack = true
describe(Support.getTestDialectTeaser("Language Util"), function() { describe(Support.getTestDialectTeaser("Language Util"), function() {
before(function(done) {
this.sequelize.options.language = 'es'
done()
})
after(function(done) { after(function(done) {
this.sequelize.options.language = 'en' this.sequelize.options.language = 'en'
done() done()
}) })
describe("Plural", function(){ describe("Plural", function(){
before(function(done) {
this.sequelize.options.language = 'es'
done()
})
it("should rename tables to their plural form...", function(done){ it("should rename tables to their plural form...", function(done){
var self = this var self = this
, table = self.sequelize.define('arbol', {name: Sequelize.STRING}) , table = self.sequelize.define('arbol', {name: Sequelize.STRING})
......
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, dialect = Support.getTestDialect()
, sinon = require('sinon')
, DataTypes = require(__dirname + "/../../lib/data-types")
chai.Assertion.includeStack = true
if (dialect.match(/^mysql/)) {
describe('[MYSQL Specific] Associations', function() {
describe('many-to-many', function() {
describe('where tables have the same prefix', function() {
it("should create a table wp_table1wp_table2s", function(done) {
var Table2 = this.sequelize.define('wp_table2', {foo: DataTypes.STRING})
, Table1 = this.sequelize.define('wp_table1', {foo: DataTypes.STRING})
, self = this
Table1.hasMany(Table2)
Table2.hasMany(Table1)
Table1.sync({ force: true }).success(function() {
Table2.sync({ force: true }).success(function() {
expect(self.sequelize.daoFactoryManager.getDAO('wp_table1swp_table2s')).to.exist
done()
})
})
})
})
describe('when join table name is specified', function() {
beforeEach(function(done){
var Table2 = this.sequelize.define('ms_table1', {foo: DataTypes.STRING})
, Table1 = this.sequelize.define('ms_table2', {foo: DataTypes.STRING})
Table1.hasMany(Table2, {joinTableName: 'table1_to_table2'})
Table2.hasMany(Table1, {joinTableName: 'table1_to_table2'})
Table1.sync({ force: true }).success(function() {
Table2.sync({ force: true }).success(function() {
done()
})
})
})
it("should not use only a specified name", function() {
expect(this.sequelize.daoFactoryManager.getDAO('ms_table1sms_table2s')).not.to.exist
expect(this.sequelize.daoFactoryManager.getDAO('table1_to_table2')).to.exist
})
})
})
describe('HasMany', function() {
beforeEach(function(done) {
//prevent periods from occurring in the table name since they are used to delimit (table.column)
this.User = this.sequelize.define('User' + Math.ceil(Math.random()*10000000), { name: DataTypes.STRING })
this.Task = this.sequelize.define('Task' + Math.ceil(Math.random()*10000000), { name: DataTypes.STRING })
this.users = null
this.tasks = null
this.User.hasMany(this.Task, {as:'Tasks'})
this.Task.hasMany(this.User, {as:'Users'})
var self = this
, users = []
, tasks = []
for (var i = 0; i < 5; ++i) {
users[users.length] = {name: 'User' + Math.random()}
}
for (var x = 0; x < 5; ++x) {
tasks[tasks.length] = {name: 'Task' + Math.random()}
}
this.User.sync({ force: true }).success(function() {
self.Task.sync({ force: true }).success(function() {
self.User.bulkCreate(users).success(function() {
self.Task.bulkCreate(tasks).success(function() {
done()
})
})
})
})
})
describe('addDAO / getDAO', function() {
beforeEach(function(done) {
var self = this
self.user = null
self.task = null
self.User.all().success(function(_users) {
self.Task.all().success(function(_tasks) {
self.user = _users[0]
self.task = _tasks[0]
done()
})
})
})
it('should correctly add an association to the dao', function(done) {
var self = this
self.user.getTasks().on('success', function(_tasks) {
expect(_tasks.length).to.equal(0)
self.user.addTask(self.task).on('success', function() {
self.user.getTasks().on('success', function(_tasks) {
expect(_tasks.length).to.equal(1)
done()
})
})
})
})
})
describe('removeDAO', function() {
beforeEach(function(done) {
var self = this
self.user = null
self.tasks = null
self.User.all().success(function(_users) {
self.Task.all().success(function(_tasks) {
self.user = _users[0]
self.tasks = _tasks
done()
})
})
})
it("should correctly remove associated objects", function(done) {
var self = this
self.user.getTasks().on('success', function(__tasks) {
expect(__tasks.length).to.equal(0)
self.user.setTasks(self.tasks).on('success', function() {
self.user.getTasks().on('success', function(_tasks) {
expect(_tasks.length).to.equal(self.tasks.length)
self.user.removeTask(self.tasks[0]).on('success', function() {
self.user.getTasks().on('success', function(_tasks) {
expect(_tasks.length).to.equal(self.tasks.length - 1)
done()
})
})
})
})
})
})
})
})
})
}
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, dialect = Support.getTestDialect()
, sinon = require('sinon')
, DataTypes = require(__dirname + "/../../lib/data-types")
chai.Assertion.includeStack = true
if (dialect.match(/^mysql/)) {
describe('[MYSQL Specific] Connector Manager', function() {
this.timeout(10000)
it('works correctly after being idle', function(done) {
var User = this.sequelize.define('User', { username: DataTypes.STRING })
, spy = sinon.spy()
User.sync({force: true}).on('success', function() {
User.create({username: 'user1'}).on('success', function() {
User.count().on('success', function(count) {
expect(count).to.equal(1)
spy()
setTimeout(function() {
User.count().on('success', function(count) {
expect(count).to.equal(1)
spy()
if (spy.calledTwice) {
done()
}
})
}, 1000)
})
})
})
})
})
}
/* jshint camelcase: false */
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, DataTypes = require(__dirname + "/../../lib/data-types")
, dialect = Support.getTestDialect()
, config = require(__dirname + "/../config/config")
chai.Assertion.includeStack = true
if (dialect.match(/^mysql/)) {
describe("[MYSQL Specific] DAOFactory", function () {
describe('constructor', function() {
it("handles extended attributes (unique)", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
username: { type: DataTypes.STRING, unique: true }
}, { timestamps: false })
expect(User.attributes).to.deep.equal({username:"VARCHAR(255) UNIQUE",id:"INTEGER NOT NULL auto_increment PRIMARY KEY"})
done()
})
it("handles extended attributes (default)", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
username: {type: DataTypes.STRING, defaultValue: 'foo'}
}, { timestamps: false })
expect(User.attributes).to.deep.equal({username:"VARCHAR(255) DEFAULT 'foo'",id:"INTEGER NOT NULL auto_increment PRIMARY KEY"})
done()
})
it("handles extended attributes (null)", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
username: {type: DataTypes.STRING, allowNull: false}
}, { timestamps: false })
expect(User.attributes).to.deep.equal({username:"VARCHAR(255) NOT NULL",id:"INTEGER NOT NULL auto_increment PRIMARY KEY"})
done()
})
it("handles extended attributes (comment)", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
username: {type: DataTypes.STRING, comment: 'This be\'s a comment'}
}, { timestamps: false })
expect(User.attributes).to.deep.equal({username:"VARCHAR(255) COMMENT 'This be\\'s a comment'",id:"INTEGER NOT NULL auto_increment PRIMARY KEY"})
done()
})
it("handles extended attributes (primaryKey)", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
username: {type: DataTypes.STRING, primaryKey: true}
}, { timestamps: false })
expect(User.attributes).to.deep.equal({username:"VARCHAR(255) PRIMARY KEY"})
done()
})
it("adds timestamps", function(done) {
var User1 = this.sequelize.define('User' + config.rand(), {})
var User2 = this.sequelize.define('User' + config.rand(), {}, { timestamps: true })
expect(User1.attributes).to.deep.equal({id:"INTEGER NOT NULL auto_increment PRIMARY KEY", updatedAt:"DATETIME NOT NULL", createdAt:"DATETIME NOT NULL"})
expect(User2.attributes).to.deep.equal({id:"INTEGER NOT NULL auto_increment PRIMARY KEY", updatedAt:"DATETIME NOT NULL", createdAt:"DATETIME NOT NULL"})
done()
})
it("adds deletedAt if paranoid", function(done) {
var User = this.sequelize.define('User' + config.rand(), {}, { paranoid: true })
expect(User.attributes).to.deep.equal({id:"INTEGER NOT NULL auto_increment PRIMARY KEY", deletedAt:"DATETIME", updatedAt:"DATETIME NOT NULL", createdAt:"DATETIME NOT NULL"})
done()
})
it("underscores timestamps if underscored", function(done) {
var User = this.sequelize.define('User' + config.rand(), {}, { paranoid: true, underscored: true })
expect(User.attributes).to.deep.equal({id:"INTEGER NOT NULL auto_increment PRIMARY KEY", deleted_at:"DATETIME", updated_at:"DATETIME NOT NULL", created_at:"DATETIME NOT NULL"})
done()
})
})
describe('primaryKeys', function() {
it("determines the correct primaryKeys", function(done) {
var User = this.sequelize.define('User' + config.rand(), {
foo: {type: DataTypes.STRING, primaryKey: true},
bar: DataTypes.STRING
})
expect(User.primaryKeys).to.deep.equal({"foo":"VARCHAR(255) PRIMARY KEY"})
done()
})
})
})
}
/* jshint camelcase: false */
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, dialect = Support.getTestDialect()
, util = require("util")
, _ = require('lodash')
, QueryGenerator = require("../../lib/dialects/mysql/query-generator")
chai.Assertion.includeStack = true
if (dialect.match(/^mysql/)) {
describe("[MYSQL Specific] QueryGenerator", function () {
var suites = {
attributesToSQL: [
{
arguments: [{id: 'INTEGER'}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: 'INTEGER', foo: 'VARCHAR(255)'}],
expectation: {id: 'INTEGER', foo: 'VARCHAR(255)'}
},
{
arguments: [{id: {type: 'INTEGER'}}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: false}}],
expectation: {id: 'INTEGER NOT NULL'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: true}}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: {type: 'INTEGER', primaryKey: true, autoIncrement: true}}],
expectation: {id: 'INTEGER auto_increment PRIMARY KEY'}
},
{
arguments: [{id: {type: 'INTEGER', defaultValue: 0}}],
expectation: {id: 'INTEGER DEFAULT 0'}
},
{
arguments: [{id: {type: 'INTEGER', unique: true}}],
expectation: {id: 'INTEGER UNIQUE'}
},
{
arguments: [{id: {type: 'INTEGER', comment: "I'm a comment!" }}],
expectation: {id: "INTEGER COMMENT 'I\\'m a comment!'" }
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`)'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', referencesKey: 'pk'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`pk`)'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', onDelete: 'CASCADE'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`) ON DELETE CASCADE'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', onUpdate: 'RESTRICT'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`) ON UPDATE RESTRICT'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: false, autoIncrement: true, defaultValue: 1, references: 'Bar', onDelete: 'CASCADE', onUpdate: 'RESTRICT'}}],
expectation: {id: 'INTEGER NOT NULL auto_increment DEFAULT 1 REFERENCES `Bar` (`id`) ON DELETE CASCADE ON UPDATE RESTRICT'}
},
],
createTableQuery: [
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255)) ENGINE=InnoDB;"
},
{
arguments: ['myTable', {title: "INTEGER COMMENT 'I\\'m a comment!'"}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` INTEGER COMMENT 'I\\'m a comment!') ENGINE=InnoDB;"
},
{
arguments: ['myTable', {title: "INTEGER"}, {comment: "I'm a comment!"}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` INTEGER) COMMENT 'I\\'m a comment!' ENGINE=InnoDB;"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)'}, {engine: 'MyISAM'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255)) ENGINE=MyISAM;"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)'}, {charset: 'utf8', collate: 'utf8_unicode_ci'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255)) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)'}, {charset: 'latin1'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255)) ENGINE=InnoDB DEFAULT CHARSET=latin1;"
},
{
arguments: ['myTable', {title: 'ENUM("A", "B", "C")', name: 'VARCHAR(255)'}, {charset: 'latin1'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` ENUM(\"A\", \"B\", \"C\"), `name` VARCHAR(255)) ENGINE=InnoDB DEFAULT CHARSET=latin1;"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)', id: 'INTEGER PRIMARY KEY'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255), `id` INTEGER , PRIMARY KEY (`id`)) ENGINE=InnoDB;"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)', otherId: 'INTEGER REFERENCES `otherTable` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255), `otherId` INTEGER, FOREIGN KEY (`otherId`) REFERENCES `otherTable` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION) ENGINE=InnoDB;"
}
],
dropTableQuery: [
{
arguments: ['myTable'],
expectation: "DROP TABLE IF EXISTS `myTable`;"
}
],
selectQuery: [
{
arguments: ['myTable'],
expectation: "SELECT * FROM `myTable`;",
context: QueryGenerator
}, {
arguments: ['myTable', {attributes: ['id', 'name']}],
expectation: "SELECT `id`, `name` FROM `myTable`;",
context: QueryGenerator
}, {
arguments: ['myTable', {where: {id: 2}}],
expectation: "SELECT * FROM `myTable` WHERE `myTable`.`id`=2;",
context: QueryGenerator
}, {
arguments: ['myTable', {where: {name: 'foo'}}],
expectation: "SELECT * FROM `myTable` WHERE `myTable`.`name`='foo';",
context: QueryGenerator
}, {
arguments: ['myTable', {where: {name: "foo';DROP TABLE myTable;"}}],
expectation: "SELECT * FROM `myTable` WHERE `myTable`.`name`='foo\\';DROP TABLE myTable;';",
context: QueryGenerator
}, {
arguments: ['myTable', {where: 2}],
expectation: "SELECT * FROM `myTable` WHERE `myTable`.`id`=2;",
context: QueryGenerator
}, {
arguments: ['foo', { attributes: [['count(*)', 'count']] }],
expectation: 'SELECT count(*) as `count` FROM `foo`;',
context: QueryGenerator
}, {
arguments: ['myTable', {where: "foo='bar'"}],
expectation: "SELECT * FROM `myTable` WHERE foo='bar';",
context: QueryGenerator
}, {
arguments: ['myTable', {order: "id DESC"}],
expectation: "SELECT * FROM `myTable` ORDER BY id DESC;",
context: QueryGenerator
}, {
arguments: ['myTable', {group: "name"}],
expectation: "SELECT * FROM `myTable` GROUP BY `name`;",
context: QueryGenerator
}, {
arguments: ['myTable', {group: ["name"]}],
expectation: "SELECT * FROM `myTable` GROUP BY `name`;",
context: QueryGenerator
}, {
arguments: ['myTable', {group: ["name", "title"]}],
expectation: "SELECT * FROM `myTable` GROUP BY `name`, `title`;",
context: QueryGenerator
}, {
arguments: ['myTable', {group: "name", order: "id DESC"}],
expectation: "SELECT * FROM `myTable` GROUP BY `name` ORDER BY id DESC;",
context: QueryGenerator
}, {
arguments: ['myTable', {limit: 10}],
expectation: "SELECT * FROM `myTable` LIMIT 10;",
context: QueryGenerator
}, {
arguments: ['myTable', {limit: 10, offset: 2}],
expectation: "SELECT * FROM `myTable` LIMIT 2, 10;",
context: QueryGenerator
}, {
title: 'uses default limit if only offset is specified',
arguments: ['myTable', {offset: 2}],
expectation: "SELECT * FROM `myTable` LIMIT 2, 18440000000000000000;",
context: QueryGenerator
}, {
title: 'multiple where arguments',
arguments: ['myTable', {where: {boat: 'canoe', weather: 'cold'}}],
expectation: "SELECT * FROM `myTable` WHERE `myTable`.`boat`='canoe' AND `myTable`.`weather`='cold';",
context: QueryGenerator
}, {
title: 'no where arguments (object)',
arguments: ['myTable', {where: {}}],
expectation: "SELECT * FROM `myTable` WHERE 1=1;",
context: QueryGenerator
}, {
title: 'no where arguments (string)',
arguments: ['myTable', {where: ''}],
expectation: "SELECT * FROM `myTable` WHERE 1=1;",
context: QueryGenerator
}, {
title: 'no where arguments (null)',
arguments: ['myTable', {where: null}],
expectation: "SELECT * FROM `myTable` WHERE 1=1;",
context: QueryGenerator
}
],
insertQuery: [
{
arguments: ['myTable', {name: 'foo'}],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo');"
}, {
arguments: ['myTable', {name: "foo';DROP TABLE myTable;"}],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo\\';DROP TABLE myTable;');"
}, {
arguments: ['myTable', {name: 'foo', birthday: new Date(Date.UTC(2011, 2, 27, 10, 1, 55))}],
expectation: "INSERT INTO `myTable` (`name`,`birthday`) VALUES ('foo','2011-03-27 10:01:55');"
}, {
arguments: ['myTable', {name: 'foo', foo: 1}],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1);"
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL);"
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL);",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1);",
context: {options: {omitNull: true}}
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: undefined}],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1);",
context: {options: {omitNull: true}}
}, {
arguments: ['myTable', {foo: false}],
expectation: "INSERT INTO `myTable` (`foo`) VALUES (false);"
}, {
arguments: ['myTable', {foo: true}],
expectation: "INSERT INTO `myTable` (`foo`) VALUES (true);"
}
],
bulkInsertQuery: [
{
arguments: ['myTable', [{name: 'foo'}, {name: 'bar'}]],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo'),('bar');"
}, {
arguments: ['myTable', [{name: "foo';DROP TABLE myTable;"}, {name: 'bar'}]],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo\\';DROP TABLE myTable;'),('bar');"
}, {
arguments: ['myTable', [{name: 'foo', birthday: new Date(Date.UTC(2011, 2, 27, 10, 1, 55))}, {name: 'bar', birthday: new Date(Date.UTC(2012, 2, 27, 10, 1, 55))}]],
expectation: "INSERT INTO `myTable` (`name`,`birthday`) VALUES ('foo','2011-03-27 10:01:55'),('bar','2012-03-27 10:01:55');"
}, {
arguments: ['myTable', [{name: 'foo', foo: 1}, {name: 'bar', foo: 2}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1),('bar',2);"
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',NULL);"
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: true}} // Note: We don't honour this because it makes little sense when some rows may have nulls and others not
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: undefined}, {name: 'bar', foo: 2, undefinedValue: undefined}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: true}} // Note: As above
}, {
arguments: ['myTable', [{name: "foo", value: true}, {name: 'bar', value: false}]],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('foo',true),('bar',false);"
}
],
updateQuery: [
{
arguments: ['myTable', {name: 'foo', birthday: new Date(Date.UTC(2011, 2, 27, 10, 1, 55))}, {id: 2}],
expectation: "UPDATE `myTable` SET `name`='foo',`birthday`='2011-03-27 10:01:55' WHERE `id`=2"
}, {
arguments: ['myTable', {name: 'foo', birthday: new Date(Date.UTC(2011, 2, 27, 10, 1, 55))}, 2],
expectation: "UPDATE `myTable` SET `name`='foo',`birthday`='2011-03-27 10:01:55' WHERE `id`=2"
}, {
arguments: ['myTable', {bar: 2}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2 WHERE `name`='foo'"
}, {
arguments: ['myTable', {name: "foo';DROP TABLE myTable;"}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `name`='foo\\';DROP TABLE myTable;' WHERE `name`='foo'"
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2,`nullValue`=NULL WHERE `name`='foo'"
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2,`nullValue`=NULL WHERE `name`='foo'",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2 WHERE `name`='foo'",
context: {options: {omitNull: true}}
}, {
arguments: ['myTable', {bar: false}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=false WHERE `name`='foo'"
}, {
arguments: ['myTable', {bar: true}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=true WHERE `name`='foo'"
}
],
deleteQuery: [
{
arguments: ['myTable', {name: 'foo'}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo' LIMIT 1"
}, {
arguments: ['myTable', 1],
expectation: "DELETE FROM `myTable` WHERE `id`=1 LIMIT 1"
},{
arguments: ['myTable', undefined, {truncate: true}],
expectation: "TRUNCATE `myTable`"
},{
arguments: ['myTable', 1, {limit: 10, truncate: true}],
expectation: "TRUNCATE `myTable`"
}, {
arguments: ['myTable', 1, {limit: 10}],
expectation: "DELETE FROM `myTable` WHERE `id`=1 LIMIT 10"
}, {
arguments: ['myTable', {name: "foo';DROP TABLE myTable;"}, {limit: 10}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo\\';DROP TABLE myTable;' LIMIT 10"
}, {
arguments: ['myTable', {name: 'foo'}, {limit: null}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo'"
}
],
addIndexQuery: [
{
arguments: ['User', ['username', 'isAdmin']],
expectation: 'CREATE INDEX user_username_is_admin ON User (username, isAdmin)'
}, {
arguments: [
'User', [
{ attribute: 'username', length: 10, order: 'ASC'},
'isAdmin'
]
],
expectation: "CREATE INDEX user_username_is_admin ON User (username(10) ASC, isAdmin)"
}, {
arguments: [
'User', ['username', 'isAdmin'], { parser: 'foo', indicesType: 'FULLTEXT', indexName: 'bar'}
],
expectation: "CREATE FULLTEXT INDEX bar ON User (username, isAdmin) WITH PARSER foo"
}
],
showIndexQuery: [
{
arguments: ['User'],
expectation: 'SHOW INDEX FROM User'
}, {
arguments: ['User', { database: 'sequelize' }],
expectation: "SHOW INDEX FROM User FROM sequelize"
}
],
removeIndexQuery: [
{
arguments: ['User', 'user_foo_bar'],
expectation: "DROP INDEX user_foo_bar ON User"
}, {
arguments: ['User', ['foo', 'bar']],
expectation: "DROP INDEX user_foo_bar ON User"
}
],
hashToWhereConditions: [
{
arguments: [{ id: [1,2,3] }],
expectation: "`id` IN (1,2,3)"
},
{
arguments: [{ id: [] }],
expectation: "`id` IN (NULL)"
},
{
arguments: [{ maple: false, bacon: true }],
expectation: "`maple`=false AND `bacon`=true"
},
{
arguments: [{ beaver: [false, true] }],
expectation: "`beaver` IN (false,true)"
},
{
arguments: [{birthday: new Date(Date.UTC(2011, 6, 1, 10, 1, 55))}],
expectation: "`birthday`='2011-07-01 10:01:55'"
},
{
arguments: [{ birthday: new Date(Date.UTC(2011, 6, 1, 10, 1, 55)),
otherday: new Date(Date.UTC(2013, 6, 2, 10, 1, 22)) }],
expectation: "`birthday`='2011-07-01 10:01:55' AND `otherday`='2013-07-02 10:01:22'"
},
{
arguments: [{ birthday: [new Date(Date.UTC(2011, 6, 1, 10, 1, 55)), new Date(Date.UTC(2013, 6, 2, 10, 1, 22))] }],
expectation: "`birthday` IN ('2011-07-01 10:01:55','2013-07-02 10:01:22')"
}
]
}
_.each(suites, function(tests, suiteTitle) {
describe(suiteTitle, function() {
tests.forEach(function(test) {
var title = test.title || 'MySQL correctly returns ' + test.expectation + ' for ' + util.inspect(test.arguments)
it(title, function(done) {
// Options would normally be set by the query interface that instantiates the query-generator, but here we specify it explicitly
var context = test.context || {options: {}};
QueryGenerator.options = context.options
var conditions = QueryGenerator[suiteTitle].apply(QueryGenerator, test.arguments)
expect(conditions).to.deep.equal(test.expectation)
done()
})
})
})
})
})
}
var chai = require('chai') var chai = require('chai')
, expect = chai.expect , expect = chai.expect
, Support = require(__dirname + '/support') , Support = require(__dirname + '/support')
, DataTypes = require(__dirname + "/../lib/data-types")
, dialect = Support.getTestDialect()
, QueryChainer = require("../lib/query-chainer") , QueryChainer = require("../lib/query-chainer")
, CustomEventEmitter = require("../lib/emitters/custom-event-emitter") , CustomEventEmitter = require("../lib/emitters/custom-event-emitter")
, _ = require('lodash')
chai.Assertion.includeStack = true chai.Assertion.includeStack = true
...@@ -16,7 +13,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () { ...@@ -16,7 +13,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () {
}) })
describe('add', function() { describe('add', function() {
it('adds a new serial item if method is passed', function(done) { it('adds a new serial item if method is passed', function(done) {
expect(this.queryChainer.serials.length).to.equal(0) expect(this.queryChainer.serials.length).to.equal(0)
this.queryChainer.add({}, 'foo') this.queryChainer.add({}, 'foo')
expect(this.queryChainer.serials.length).to.equal(1) expect(this.queryChainer.serials.length).to.equal(1)
...@@ -57,7 +54,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () { ...@@ -57,7 +54,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () {
this.queryChainer.run().success(function(results) { this.queryChainer.run().success(function(results) {
expect(results).to.exist expect(results).to.exist
expect(results.length).to.equal(1) expect(results).to.have.length(1)
expect(results[0]).to.equal(1) expect(results[0]).to.equal(1)
done() done()
}) })
...@@ -75,7 +72,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () { ...@@ -75,7 +72,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () {
this.queryChainer.add(emitter3) this.queryChainer.add(emitter3)
this.queryChainer.run().success(function(results) { this.queryChainer.run().success(function(results) {
expect(results.length).to.equal(3) expect(results).to.have.length(3)
expect(results).to.include.members([1,2,3]) expect(results).to.include.members([1,2,3])
done() done()
}) })
...@@ -126,7 +123,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () { ...@@ -126,7 +123,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () {
this.queryChainer.runSerially().success(function(results) { this.queryChainer.runSerially().success(function(results) {
expect(results).to.exist expect(results).to.exist
expect(results.length).to.equal(1) expect(results).to.have.length(1)
expect(results[0]).to.equal(1) expect(results[0]).to.equal(1)
done() done()
}) })
...@@ -142,7 +139,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () { ...@@ -142,7 +139,7 @@ describe(Support.getTestDialectTeaser("QueryChainer"), function () {
this.queryChainer.add(emitter3, 'run') this.queryChainer.add(emitter3, 'run')
this.queryChainer.runSerially().success(function(results) { this.queryChainer.runSerially().success(function(results) {
expect(results.length).to.equal(3) expect(results).to.have.length(3)
expect(results).to.contain.members([1,2,3]) expect(results).to.contain.members([1,2,3])
done() done()
}) })
......
/* jshint camelcase: false */
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, DataTypes = require(__dirname + "/../../lib/data-types")
, dialect = Support.getTestDialect()
, dbFile = __dirname + '/test.sqlite'
, storages = [dbFile]
chai.Assertion.includeStack = true
if (dialect === 'sqlite') {
describe('[SQLITE Specific] DAOFactory', function() {
after(function(done) {
this.sequelize.options.storage = ':memory:'
done()
})
beforeEach(function(done) {
this.sequelize.options.storage = dbFile
this.User = this.sequelize.define('User', {
age: DataTypes.INTEGER,
name: DataTypes.STRING,
bio: DataTypes.TEXT
})
this.User.sync({ force: true }).success(function() {
done()
})
})
storages.forEach(function(storage) {
describe('with storage "' + storage + '"', function() {
after(function(done) {
if (storage === dbFile) {
require("fs").writeFile(dbFile, '', function() {
done()
})
}
})
describe('create', function() {
it('creates a table entry', function(done) {
var self = this
this.User.create({ age: 21, name: 'John Wayne', bio: 'noot noot' }).success(function(user) {
expect(user.age).to.equal(21)
expect(user.name).to.equal('John Wayne')
expect(user.bio).to.equal('noot noot')
self.User.all().success(function(users) {
var usernames = users.map(function(user) {
return user.name
})
expect(usernames).to.contain('John Wayne')
done()
})
})
})
it('should allow the creation of an object with options as attribute', function(done) {
var Person = this.sequelize.define('Person', {
name: DataTypes.STRING,
options: DataTypes.TEXT
})
Person.sync({ force: true }).success(function() {
var options = JSON.stringify({ foo: 'bar', bar: 'foo' })
Person.create({
name: 'John Doe',
options: options
}).success(function(people) {
expect(people.options).to.deep.equal(options)
done()
})
})
})
it('should allow the creation of an object with a boolean (true) as attribute', function(done) {
var Person = this.sequelize.define('Person', {
name: DataTypes.STRING,
has_swag: DataTypes.BOOLEAN
})
Person.sync({ force: true }).success(function() {
Person.create({
name: 'John Doe',
has_swag: true
}).success(function(people) {
expect(people.has_swag).to.be.ok
done()
})
})
})
it('should allow the creation of an object with a boolean (false) as attribute', function(done) {
var Person = this.sequelize.define('Person', {
name: DataTypes.STRING,
has_swag: DataTypes.BOOLEAN
})
Person.sync({ force: true }).success(function() {
Person.create({
name: 'John Doe',
has_swag: false
}).success(function(people) {
expect(people.has_swag).to.not.be.ok
done()
})
})
})
})
describe('.find', function() {
beforeEach(function(done) {
this.User.create({name: 'user', bio: 'footbar'}).success(function() {
done()
})
})
it("finds normal lookups", function(done) {
this.User.find({ where: { name:'user' } }).success(function(user) {
expect(user.name).to.equal('user')
done()
})
})
it("should make aliased attributes available", function(done) {
this.User.find({ where: { name:'user' }, attributes: ['id', ['name', 'username']] }).success(function(user) {
expect(user.username).to.equal('user')
done()
})
})
})
describe('.all', function() {
beforeEach(function(done) {
this.User.bulkCreate([
{name: 'user', bio: 'foobar'},
{name: 'user', bio: 'foobar'}
]).success(function() {
done()
})
})
it("should return all users", function(done) {
this.User.all().on('success', function(users) {
expect(users).to.have.length(2)
done()
})
})
})
describe('.min', function() {
it("should return the min value", function(done) {
var self = this
, users = []
for (var i = 2; i < 5; i++) {
users[users.length] = {age: i}
}
this.User.bulkCreate(users).success(function() {
self.User.min('age').on('success', function(min) {
expect(min).to.equal(2)
done()
})
})
})
})
describe('.max', function() {
it("should return the max value", function(done) {
var self = this
, users = []
for (var i = 2; i <= 5; i++) {
users[users.length] = {age: i}
}
this.User.bulkCreate(users).success(function() {
self.User.max('age').on('success', function(min) {
expect(min).to.equal(5)
done()
})
})
})
})
})
})
})
}
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, DataTypes = require(__dirname + "/../../lib/data-types")
, dialect = Support.getTestDialect()
chai.Assertion.includeStack = true
if (dialect === 'sqlite') {
describe('[SQLITE Specific] DAO', function() {
beforeEach(function(done) {
this.User = this.sequelize.define('User', {
username: DataTypes.STRING
})
this.User.sync({ force: true }).success(function() {
done()
})
})
describe('findAll', function() {
it("handles dates correctly", function(done) {
var self = this
this.User
.create({ username: 'user', createdAt: new Date(2011, 04, 04) })
.success(function() {
self.User.create({ username: 'new user' }).success(function() {
self.User.findAll({
where: ['createdAt > ?', new Date(2012, 01, 01)]
}).success(function(users) {
expect(users).to.have.length(1)
done()
})
})
})
})
})
})
}
var chai = require('chai')
, expect = chai.expect
, Support = require(__dirname + '/../support')
, DataTypes = require(__dirname + "/../../lib/data-types")
, dialect = Support.getTestDialect()
, util = require("util")
, _ = require('lodash')
, QueryGenerator = require("../../lib/dialects/sqlite/query-generator")
chai.Assertion.includeStack = true
if (dialect === 'sqlite') {
describe('[SQLITE Specific] QueryGenerator', function() {
beforeEach(function(done) {
this.User = this.sequelize.define('User', {
username: DataTypes.STRING
})
this.User.sync({ force: true }).success(function() {
done()
})
})
var suites = {
attributesToSQL: [
{
arguments: [{id: 'INTEGER'}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: 'INTEGER', foo: 'VARCHAR(255)'}],
expectation: {id: 'INTEGER', foo: 'VARCHAR(255)'}
},
{
arguments: [{id: {type: 'INTEGER'}}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: false}}],
expectation: {id: 'INTEGER NOT NULL'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: true}}],
expectation: {id: 'INTEGER'}
},
{
arguments: [{id: {type: 'INTEGER', primaryKey: true, autoIncrement: true}}],
expectation: {id: 'INTEGER PRIMARY KEY AUTOINCREMENT'}
},
{
arguments: [{id: {type: 'INTEGER', defaultValue: 0}}],
expectation: {id: 'INTEGER DEFAULT 0'}
},
{
arguments: [{id: {type: 'INTEGER', unique: true}}],
expectation: {id: 'INTEGER UNIQUE'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`)'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', referencesKey: 'pk'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`pk`)'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', onDelete: 'CASCADE'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`) ON DELETE CASCADE'}
},
{
arguments: [{id: {type: 'INTEGER', references: 'Bar', onUpdate: 'RESTRICT'}}],
expectation: {id: 'INTEGER REFERENCES `Bar` (`id`) ON UPDATE RESTRICT'}
},
{
arguments: [{id: {type: 'INTEGER', allowNull: false, defaultValue: 1, references: 'Bar', onDelete: 'CASCADE', onUpdate: 'RESTRICT'}}],
expectation: {id: 'INTEGER NOT NULL DEFAULT 1 REFERENCES `Bar` (`id`) ON DELETE CASCADE ON UPDATE RESTRICT'}
},
],
createTableQuery: [
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255));"
},
{
arguments: ['myTable', {title: 'ENUM("A", "B", "C")', name: 'VARCHAR(255)'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` ENUM(\"A\", \"B\", \"C\"), `name` VARCHAR(255));"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)', id: 'INTEGER PRIMARY KEY'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255), `id` INTEGER PRIMARY KEY);"
},
{
arguments: ['myTable', {title: 'VARCHAR(255)', name: 'VARCHAR(255)', otherId: 'INTEGER REFERENCES `otherTable` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION'}],
expectation: "CREATE TABLE IF NOT EXISTS `myTable` (`title` VARCHAR(255), `name` VARCHAR(255), `otherId` INTEGER REFERENCES `otherTable` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION);"
}
],
insertQuery: [
{
arguments: ['myTable', { name: 'foo' }],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo');"
}, {
arguments: ['myTable', { name: "'bar'" }],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('''bar''');"
}, {
arguments: ['myTable', { name: "bar", value: null }],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('bar',NULL);"
}, {
arguments: ['myTable', { name: "bar", value: undefined }],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('bar',NULL);"
}, {
arguments: ['myTable', { name: "foo", value: true }],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('foo',1);"
}, {
arguments: ['myTable', { name: "foo", value: false }],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('foo',0);"
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL);"
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL);",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: null}],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1);",
context: {options: {omitNull: true}}
}, {
arguments: ['myTable', {name: 'foo', foo: 1, nullValue: undefined}],
expectation: "INSERT INTO `myTable` (`name`,`foo`) VALUES ('foo',1);",
context: {options: {omitNull: true}}
}
],
bulkInsertQuery: [
{
arguments: ['myTable', [{name: 'foo'}, {name: 'bar'}]],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('foo'),('bar');"
}, {
arguments: ['myTable', [{name: "'bar'"}, {name: 'foo'}]],
expectation: "INSERT INTO `myTable` (`name`) VALUES ('''bar'''),('foo');"
}, {
arguments: ['myTable', [{name: "bar", value: null}, {name: 'foo', value: 1}]],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('bar',NULL),('foo',1);"
}, {
arguments: ['myTable', [{name: "bar", value: undefined}, {name: 'bar', value: 2}]],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('bar',NULL),('bar',2);"
}, {
arguments: ['myTable', [{name: "foo", value: true}, {name: 'bar', value: false}]],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('foo',1),('bar',0);"
}, {
arguments: ['myTable', [{name: "foo", value: false}, {name: 'bar', value: false}]],
expectation: "INSERT INTO `myTable` (`name`,`value`) VALUES ('foo',0),('bar',0);"
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);"
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: true}} // Note: We don't honour this because it makes little sense when some rows may have nulls and others not
}, {
arguments: ['myTable', [{name: 'foo', foo: 1, nullValue: null}, {name: 'bar', foo: 2, nullValue: null}]],
expectation: "INSERT INTO `myTable` (`name`,`foo`,`nullValue`) VALUES ('foo',1,NULL),('bar',2,NULL);",
context: {options: {omitNull: true}} // Note: As above
}
],
updateQuery: [
{
arguments: ['myTable', { name: 'foo' }, { id: 2 }],
expectation: "UPDATE `myTable` SET `name`='foo' WHERE `id`=2"
}, {
arguments: ['myTable', { name: "'bar'" }, { id: 2 }],
expectation: "UPDATE `myTable` SET `name`='''bar''' WHERE `id`=2"
}, {
arguments: ['myTable', { name: 'bar', value: null }, { id: 2 }],
expectation: "UPDATE `myTable` SET `name`='bar',`value`=NULL WHERE `id`=2"
}, {
arguments: ['myTable', { name: 'bar', value: undefined }, { id: 2 }],
expectation: "UPDATE `myTable` SET `name`='bar',`value`=NULL WHERE `id`=2"
}, {
arguments: ['myTable', { flag: true }, { id: 2 }],
expectation: "UPDATE `myTable` SET `flag`=1 WHERE `id`=2"
}, {
arguments: ['myTable', { flag: false }, { id: 2 }],
expectation: "UPDATE `myTable` SET `flag`=0 WHERE `id`=2"
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2,`nullValue`=NULL WHERE `name`='foo'"
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2,`nullValue`=NULL WHERE `name`='foo'",
context: {options: {omitNull: false}}
}, {
arguments: ['myTable', {bar: 2, nullValue: null}, {name: 'foo'}],
expectation: "UPDATE `myTable` SET `bar`=2 WHERE `name`='foo'",
context: {options: {omitNull: true}}
}
],
deleteQuery: [
{
arguments: ['myTable', {name: 'foo'}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo'"
}, {
arguments: ['myTable', 1],
expectation: "DELETE FROM `myTable` WHERE `id`=1"
}, {
arguments: ['myTable', 1, {truncate: true}],
expectation: "DELETE FROM `myTable` WHERE `id`=1"
}, {
arguments: ['myTable', 1, {limit: 10}],
expectation: "DELETE FROM `myTable` WHERE `id`=1"
}, {
arguments: ['myTable', {name: "foo';DROP TABLE myTable;"}, {limit: 10}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo'';DROP TABLE myTable;'"
}, {
arguments: ['myTable', {name: 'foo'}, {limit: null}],
expectation: "DELETE FROM `myTable` WHERE `name`='foo'"
}
]
}
_.each(suites, function(tests, suiteTitle) {
describe(suiteTitle, function() {
tests.forEach(function(test) {
var title = test.title || 'SQLite correctly returns ' + test.expectation + ' for ' + util.inspect(test.arguments)
it(title, function(done) {
// Options would normally be set by the query interface that instantiates the query-generator, but here we specify it explicitly
var context = test.context || {options: {}};
QueryGenerator.options = context.options
var conditions = QueryGenerator[suiteTitle].apply(QueryGenerator, test.arguments)
expect(conditions).to.deep.equal(test.expectation)
done()
})
})
})
})
})
}
File mode changed
...@@ -2,10 +2,8 @@ var fs = require('fs') ...@@ -2,10 +2,8 @@ var fs = require('fs')
, Sequelize = require(__dirname + "/../index") , Sequelize = require(__dirname + "/../index")
, DataTypes = require(__dirname + "/../lib/data-types") , DataTypes = require(__dirname + "/../lib/data-types")
, config = require(__dirname + "/config/config") , config = require(__dirname + "/config/config")
, chai = require('chai')
, expect = chai.expect
module.exports = { var Support = {
Sequelize: Sequelize, Sequelize: Sequelize,
initTests: function(options) { initTests: function(options) {
...@@ -113,3 +111,18 @@ module.exports = { ...@@ -113,3 +111,18 @@ module.exports = {
return "[" + dialect.toUpperCase() + "] " + moduleName return "[" + dialect.toUpperCase() + "] " + moduleName
} }
} }
var sequelize = Support.createSequelizeInstance({ dialect: Support.getTestDialect() })
before(function(done) {
this.sequelize = sequelize
done()
})
afterEach(function(done) {
Support.clearDatabase(this.sequelize, function() {
done()
})
})
module.exports = Support
var Support = require(__dirname + '/support')
, dialect = Support.getTestDialect()
var sequelize = Support.createSequelizeInstance({ dialect: dialect })
before(function(done) {
this.sequelize = sequelize
done()
})
afterEach(function(done) {
Support.clearDatabase(this.sequelize, done)
})
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!