Тестирование проверок MongooseJs - PullRequest
7 голосов
/ 10 февраля 2012

Кто-нибудь знает, как проверить валидации Mongoose?

Например, у меня есть следующая схема (как пример):

var UserAccount = new Schema({
    user_name       : { type: String, required: true, lowercase: true, trim: true, index: { unique: true }, validate: [ validateEmail, "Email is not a valid email."]  }, 
    password        : { type: String, required: true },
    date_created    : { type: Date, required: true, default: Date.now }
}); 

Метод validateEmail определяется следующим образом:

// Email Validator
function validateEmail (val) {
    return /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,4}$/.test(val);
}

Я хочу проверить проверки. Конечным результатом является то, что я хочу иметь возможность проверять валидации, и в зависимости от того, что происходит, я могу написать другие тесты, которые проверяют взаимодействие между этими частями кода. Пример: пользователь пытается зарегистрироваться с тем же именем пользователя, которое используется (адрес электронной почты уже используется). Мне нужен тест, который я действительно могу перехватить или увидеть, что проверка работает БЕЗ попадания в БД. Я НЕ хочу бить Монго во время этих тестов. Это должны быть тесты UNIT, а не интеграционные тесты. :)

Спасибо!

Ответы [ 2 ]

11 голосов
/ 15 февраля 2012

У меня недавно была такая же проблема.

Прежде всего, я бы порекомендовал проверить валидаторы самостоятельно. Просто переместите их в отдельный файл и экспортируйте имеющиеся у вас функции проверки.

Это позволяет легко разделять ваши модели на отдельные файлы, поскольку вы можете использовать эти валидаторы в разных моделях.

Вот пример тестирования валидаторов самостоятельно:

// validators.js
exports.validatePresenceOf = function(value){ ... }
exports.validateEmail = function(value){ ... }

Вот пример теста для этого (с помощью mocha + should):

// validators.tests.js
var validator = require('./validators')

// Example test
describe("validateEmail", function(){
   it("should return false when invalid email", function(){
       validator.validateEmail("asdsa").should.equal(false)
   })      
})

Теперь для более сложной части:)

Для проверки работоспособности ваших моделей без доступа к базе данных существует функция проверки, которую можно вызывать непосредственно в вашей модели.

Вот пример того, как я сейчас это делаю:

describe("validating user", function(){  
  it("should have errors when email is invalid", function(){
    var user = new User();
    user.email = "bad email!!" 
    user.validate(function(err){      
      err.errors.email.type.should.equal("Email is invalid")
    })
  })

  it("should have no errors when email is valid", function(){
    var user = new User();
    user.email = "test123@email.com"
    user.validate(function(err){
      assert.equal(err, null)
    })
  })
})   

Обратный вызов валидатора возвращает объект ошибки, который выглядит примерно так:

{ message: 'Validation failed',
    name: 'ValidationError',
    errors: 
        { email: 
           { message: 'Validator "Email is invalid" failed for path email',
             name: 'ValidatorError',
             path: 'email',
             type: 'Email is invalid' 
           } 
        } 
}

Я все еще новичок в nodeJS и mongoose, но именно так я тестирую свои модели + валидаторы, и, похоже, до сих пор получалось довольно хорошо.

2 голосов
/ 29 августа 2015

Вы должны использовать метод validate () в качестве обещания и протестировать его с помощью инструмента, который делает утверждения для асинхронного материала (например: Chai as Promised ).

Прежде всего, потребуйте библиотеку обещаний и переключитесь на поставщика обещаний (например, Q):

mongoose.Promise = require('q').Promise;

Затем просто используйте утверждения об обещаниях:

    it('should show errors on wrong email', function() {
        user = new UserModel({
            email: 'wrong email adress'
        });
        return expect(user.validate()).to.be.rejected;
    });

    it('should not show errors on valid email adress', function() {
        user = new UserModel({
            email: 'test@test.io'
        });
        return expect(user.validate()).to.be.fulfilled;
    });
...