-1

我正在开发一个将基于友谊的关系添加到模式的模块。

我基本上是在尝试做这个人想做的事情(AFAIK,应该可以工作——这令人沮丧)

为什么永远不会达到它的回调find(...)FriendshipSchema.statics.getFriends

编辑- 请允许我解释预期的执行流程......

里面accounts.js

  1. 需要 'friends-of-friends' 模块(加载friends-of-friends/index.js
    1. 需要friends-of-friends/friendship.js它导出一个创建FriendshipSchema、添加静态方法、返回Friendship模型的函数。
    2. 需要friends-of-friends/plugin.js它导出 mongoose 插件,该插件将静态和实例方法添加到`AccountSchema.
  2. 使用FriendsOfFriends.plugin(参见friends-of-friends/index.js)从friends-of-friends/plugin.js
  3. 定义AccountSchema.statics.search哪些调用this.getFriends.
    由于this在编译后引用Account模型,并且由于添加了插件schema.statics.getFriends,因此调用this.getFriendsinsideAccountSchema.statics.search将按schema.statics.getFriends定义调用 in friends-of-friends/plugin.js,它将调用Friendship.getFriends(由FriendshipSchema.statics.getFriendsin定义friends-of-friends/friendship.js)调用this.find(...)应该转换为 Friendship.find(...)`
  4. 检索帐户文档后,我account.search('foo', function (...) {...});调用了FriendshipSchema.statics.getFriendsfind

我没有收到任何错误,所以我知道这是一个逻辑问题,但我不确定为什么事情会挂在它们所在的位置......

编辑- 请参阅下面的答案,我还需要编译模型才能调用find它们。

account.js

var mongoose = require('mongoose'),
    passportLocalMongoose = require('passport-local-mongoose');

var FriendsOfFriends = require('friends-of-friends')();

// define the AccountSchema
// username, password, etc are added by passportLocalMongoose plugin
var AccountSchema = new mongoose.Schema({
    created:        { type: Date,       default:    Date.now                    },
    profile: {
        displayName:    { type: String,     required:   true,       unique : true,  index: true     },
        firstName:      { type: String,     required:   true,       trim: true,     index: true     }, 
        lastName:       { type: String,     required:   true,       trim: true,     index: true     }, 
    }
});

// plugin the FriendsOfFriends plugin to incorporate relationships and privacy
AccountSchema.plugin(FriendsOfFriends.plugin, FriendsOfFriends.options);

AccountSchema.statics.search = function (userId, term, done) {
    debug('search')

    var results = {
            friends: [],
            friendsOfFriends: [],
            nonFriends: []
        },
        self=this;

    this.getFriends(userId, function (err, friends) {

       // never reaches this callback!

    });

};

AccountSchema.methods.search = function (term, done) {
    debug('method:search')
    AccountSchema.statics.search(this._id, term, done);
};

module.exports = mongoose.model('Account', AccountSchema);

朋友的朋友/index.js

/**
 * @author  Jeff Harris
 * @ignore
 */

var debug = require('debug')('friends-of-friends');
    friendship = require('./friendship'),
    plugin = require('./plugin'),
    privacy = require('./privacy'),
    relationships = require('./relationships'),
    utils = require('techjeffharris-utils');

module.exports = function FriendsOfFriends(options) {

    if (!(this instanceof FriendsOfFriends)) {
      return new FriendsOfFriends(options);
    } 

    var defaults = {
        accountName:    'Account',
        friendshipName: 'Friendship', 
        privacyDefault: privacy.values.NOBODY
    };

    this.options = utils.extend(defaults, options);

    /**
     * The Friendship model
     * @type {Object}
     * @see  [friendship]{@link module:friendship}
     */
    this.friendship = friendship(this.options);

    /**
     * mongoose plugin
     * @type {Function}
     * @see  [plugin]{@link module:plugin}
     */
    this.plugin = plugin;

    debug('this.friendship', this.friendship);

};

朋友的朋友/friendship.js

var debug = require('debug')('friends-of-friends:friendship'),
    mongoose = require('mongoose'),
    privacy = require('./privacy'),
    relationships = require('./relationships'),
    utils = require('techjeffharris-utils');

module.exports = function friendshipInit(options) {

    var defaults = {
        accountName:    'Account',
        friendshipName: 'Friendship',
        privacyDefault: privacy.values.NOBODY
    };

    options = utils.extend(defaults, options);

    debug('options', options);

    var ObjectId = mongoose.Schema.Types.ObjectId;

    var FriendshipSchema = new mongoose.Schema({
        requester: { type: ObjectId, ref: options.accountName, required: true, index: true },
        requested: { type: ObjectId, ref: options.accountName, required: true, index: true },
        status: { type: String, default: 'Pending', index: true},
        dateSent: { type: Date, default: Date.now, index: true },
        dateAccepted: { type: Date, required: false, index: true }
    });

    ...

    FriendshipSchema.statics.getFriends = function (accountId, done) {
        debug('getFriends')

        var model = mongoose.model(options.friendshipName, schema),
            friendIds = [];

        var conditions = { 
            '$or': [
                { requester: accountId },
                { requested: accountId }
            ],
            status: 'Accepted'
        };

        debug('conditions', conditions);

        model.find(conditions, function (err, friendships) {
            debug('this callback is never reached!');

            if (err) {
                done(err);
            } else { 
                debug('friendships', friendships);

                friendships.forEach(function (friendship) {
                    debug('friendship', friendship);

                    if (accountId.equals(friendship.requester)) {
                        friendIds.push(friendship.requested);
                    } else {
                        friendIds.push(friendship.requester);
                    }

                });

                debug('friendIds', friendIds);

                done(null, friendIds);
            }

        });

        debug('though the find operation is executed...');
    };

    ...

    return mongoose.model(options.friendshipName, FriendshipSchema);
};

朋友的朋友/plugin.js

var debug = require('debug')('friends-of-friends:plugin'),
    mongoose = require('mongoose'),
    privacy = require('./privacy'),
    relationships = require('./relationships'),
    utils = require('techjeffharris-utils');

module.exports = function friendshipPlugin (schema, options) {

    var defaults = {
        accountName:    'Account',
        friendshipName: 'Friendship',
        privacyDefault: privacy.values.NOBODY
    };

    options = utils.extend(defaults, options);

    var Friendship = mongoose.model(options.friendshipName);

    ...

    schema.statics.getFriends = function (accountId, done) {
        debug('getFriends')

        var model = mongoose.model(options.accountName, schema);

        var select = '_id created email privacy profile';

        Friendship.getFriends(accountId, function (err, friendIds) {
            if (err) {
                done(err);
            } else {
                model.find({ '_id' : { '$in': friendIds } }, select, done);
            }
        });
    };

    ...

    schema.methods.getFriends = function (done) {
        schema.statics.getFriends(this._id, done);
    };
};
4

1 回答 1

0

该问题与需要哪个猫鼬实例有关。

在我的主应用程序中,我需要 mongoose from app/node_modules/mongoose而我的friends-of-friends模块——将 mongoose 列为依赖package.json项——需要 mongoose from app/node_modules/friends-of-friends/node_modules/mongoose,它创建了两个单独的 mongoose 实例,这使得事情无法正常工作。

我删除了 mongoose 作为依赖项,删除了嵌套node_modules文件夹,并且 vioala,它再次起作用了 :)

应该有RTFM

app/
|   lib/
|   node_modules/ 
|   |   mongoose/             <-- main app required here
|   |   friends-of-friends/
|   |   |   node_modules/     <-- deleted; mongoose was only dep
|   |   |   |   mongoose/     <-- friends-of-friends module required here
|   server.js
于 2014-12-16T11:18:36.997 回答