猫鼬辅助方法没有 findOne 方法



如何添加帮助程序方法来查找和保存猫鼬中的对象。 一个朋友告诉我使用辅助方法,但我一天后无法让它们工作。 我总是收到错误,说findOne()save()不存在,或者下一个回调未定义(当节点编译时......在我执行之前):

我尝试过_schema.方法,_schema.静态...什么都没用...

var email = require('email-addresses'),
    mongoose = require('mongoose'),
    strings = require('../../utilities/common/strings'),
    uuid = require('node-uuid'),
    validator = require('validator');
var _schema = new mongoose.Schema({
    _id: {
        type: String,
        trim: true,
        lowercase: true,
        default: uuid.v4
    },
    n: {                    // Name
        type: String,
        required: true,
        trim: true,
        lowercase: true,
        unique: true,
        index: true
    }
});
//_schema.index({
//    d: 1,
//    n: 1
//}, { unique: true });
_schema.pre('save', function (next) {
    if (!this.n || strings.isNullOrWhitespace(this.n)){
        self.invalidate('n', 'Domain name required but not supplied');
        return next(new Error('Domain name required but not supplied'));
    }
    var a = email.parseOneAddress('test@' + this.n);
    if (!a || !a.local || !a.domain){
        self.invalidate('n', 'Name is not valid domain name');
        return next(new Error('Name is not valid domain name'));
    }
    next();
});
_schema.statics.validateForSave = function (next) {
    if (!this.n || strings.isNullOrWhitespace(this.n)){
        return next(new Error('Domain name required but not supplied'));
    }
    var a = email.parseOneAddress('test@' + this.n);
    if (!a || !a.local || !a.domain){
        return next(new Error('Name is not valid domain name'));
    }
    next();
}
_schema.statics.findUnique = function (next) {
    this.validateForSave(function(err){
        if (err){ return next(err); }
        mongoose.model('Domain').findOne({ n: this.n }, next);
        //this.findOne({ n: this.n }, next);
    });
}
_schema.statics.init = function (next) {
    this.findUnique(function(err){
        if (err){ return next(err); }
        this.save(next);
    });
}
var _model = mongoose.model('Domain', _schema);
module.exports = _model;
我相信

您因为使用this而遇到了问题。每次输入一个新函数时this 的上下文都在变化。您可以在 mdn 阅读有关this的更多信息。

此外,您的回调不允许将任何内容传递到 mongoose 方法中。例如,如果我要创建最基本的"保存"方法,我会执行以下操作:

_schema.statics.basicCreate = function(newDocData, next) {
  new _model(newDocData).save(next);
}

现在,如果我想在域集合中搜索唯一文档,我将使用以下方法:

_schema.statics.basicSearch = function(uniqueName, next) {
  var query = {n: uniqueName};
  _model.findOne(query, function(err, myUniqueDoc) {
    if (err) return next(err);
    if (!myUniqueDoc) return next(new Error("No Domain with " + uniqueName + " found"));
    next(null, myNewDoc);
  });
}

猫鼬内置了对你正在做的事情的验证:

_schema.path("n").validate(function(name) {
    return name.length;
}, "Domain name is required");

_schema.path("n").validate(function(name) {
    var a = email.parseOneAddress("test@" + name);
    if (!a || !a.local || !a.domain) {
        return false;
    }
    return true;
}, "Name is not a valid domain name");

它返回一个布尔值。如果为 false,则使用声明的消息将错误传递给.save()回调。对于验证唯一性:

_schema.path("n").validate(function(name, next) {
    var self = this;
    this.model("Domain").findOne({n: name}, function(err, domain) {
        if (err) return next(err);
        if (domain) {
            if (self._id === domain._id) {
                return next(true);
            }
            return next(false);
        }
        return next(true);
    });
}, "This domain is already taken");

您在此处使用 self = this,以便可以访问findOne()回调中的文档。 如果名称存在并且找到的结果不是文档本身,则false将传递给回调。

我试过_schema.方法,_schema.statics

澄清一下,.statics对模型进行操作,.methods对文档进行操作。Zane 给出了一个很好的静态示例,所以这里有一个方法示例:

_schema.methods.isDotCom = function() {
    return (/.com/).test(this.n);
}
var org = new Domain({n: "stuff.org"});
var com = new Domain({n: "things.com"});
org.isDotCom(); // false
com.isDotCom(); // true

观点:让猫鼬做验证是很整洁的,但很容易忘记它正在发生。您可能还希望在应用的一个区域中进行一些验证,同时在其他地方使用不同的验证。我会避免使用其中的大部分,除非你明确知道你每次都必须做同样的事情,而且永远不必这样做。

方法/静态是另一回事。调用isDotCom()非常方便,而不是每次需要检查时都写出正则表达式测试。它执行单个简单的任务,为您节省一些键入内容并使您的代码更具可读性。使用布尔检查方法可以增加大量的可读性。定义像findByName(Zane的basicSearch)这样的静态数据是很好的,当你知道你要重复做一个简单的查询时。

将猫鼬视为实用程序,而不是核心功能。

最新更新