mongoose:填充有区别的子文档

问题描述 投票:0回答:1

我想填充子文档的字段,它是常见模式的可区分元素(

Notificationable
区分为
Message
FriendRequest
)。

这个问题与这个问题非常相似:mongoosejs: populated an array of objectId's from different schemas,这个问题两年前还没有解决。由于猫鼬进化了,鉴别器也进化了,我再次问这个问题。

到目前为止我尝试过的:

Notification.find({_id: 'whatever'})
    .populate({
        path: 'payload',
        match: {type: 'Message'},
        populate: ['author', 'messageThread']
    })
    .populate({
        path: 'payload',
        match: {type: 'FriendRequest'},
        populate: ['to', 'from']
    })
    .exec();

这不起作用,因为路径是相同的。 所以我尝试了:

Notification.find({_id: 'whatever'})
    .populate({
        path: 'payload',
        populate: [
            {
                path: 'messageThread',
                match: {type: 'Message'},
            },
            {
                path: 'author',
                match: {type: 'Message'},
            },
            {
                path: 'from',
                match: {type: 'FriendRequest'},
            },
            {
                path: 'to',
                match: {type: 'FriendRequest'},
            },

        ]
    })
    .exec();

这也不起作用,可能是因为匹配是在子文档中执行的,因此没有字段

type

这个问题有什么解决办法吗?


这是我的(主要)模型,我没有提供 User 或 MessageThread。

主要文档:

const NotificationSchema = new Schema({
    title: String,
    payload: {
        type: Schema.Types.ObjectId,
        ref: 'Notificationable'
    });
mongoose.model('Notification', NotificationSchema);

有效负载父架构

let NotificationableSchema = new Schema(
    {},
    {discriminatorKey: 'type', timestamps: true}
);
mongoose.model('Notificationable', NotificationableSchema);

以及两种可区分的可能性:

let Message = new Schema({
    author: {
        type: Schema.Types.ObjectId,
        ref: 'User'
    },
    messageThread: {
        type: Schema.Types.ObjectId, 
        ref: 'MessageThread'
    }
}
Notificationable.discriminator('Message', Message);

并且:

let FriendRequest = new Schema({
    from: {
        type: Schema.Types.ObjectId,
        ref: 'User'
    },
    to: {
        type: Schema.Types.ObjectId,
        ref: 'User'
    }
}
Notificationable.discriminator('FriendRequest', FriendRequest);
node.js mongodb mongoose mongoose-populate discriminator
1个回答
0
投票

我已经尝试过这个方法来解决我遇到的类似问题,我认为它可以帮助您解决问题

Notifiable.findOne({_id: 'whatever'})
    .populate({
        path: 'payload',
        populate: { path: '__t' }, // Populating the discriminator key
        model: function(doc) {
            // Choose the appropriate discriminator model based on the value of the discriminator key
            switch (doc.payload.__t) {
                case 'Message':
                    return Message;
                case 'FriendRequest':
                    return FriendRequest;
                default:
                    throw new Error('Invalid discriminator value');
            }
        }
    })

您还应该将模型导入到调用此代码片段的同一文件中,无论是控制器文件还是服务文件

© www.soinside.com 2019 - 2024. All rights reserved.