Sailsjs在beforeCreate期间向模型添加一对多关联

时间:2015-01-15 19:54:13

标签: sails.js

无论何时创建新用户,我都会尝试从用户向宠物提供默认关联。

Model :: User.js

    var User = {
        attributes: {
            name: {type: 'string'},
            // Add a One Way Relation to pet model
            pets: {
                collection: 'pet'
            },
        },

      /*** This did not work ***/
      beforeCreate: function (user, next) {
        var defaultPet = {name: 'Default Pet 1'};
        Pet.find(defaultPet).exec(function(err, pet) {
            user.name = "BEFORECREATE",
            user.pets = pet[0].id;
            next();
        });
      },

    }

module.exports = User;

但是,当创建新记录时,user.pet为[],但user.name更改为" BEFORECREATE"。

如何为新用户自动获取user.pets = [{name:'默认宠物1'}]?

或者是否有更好的地方设置此类默认值?

-----更新:更多信息

我目前正在使用sails-disk。

型号:Pet.js

module.exports = {
  attributes: {
    name: {
        type: 'string',
        required: true
    }
  }
};

1 个答案:

答案 0 :(得分:2)

您无法在beforeCreate等生命周期回调中为模型添加关联。目前,Waterline会在生命周期回调运行之前查找并处理像这些这样的“嵌套模型”,因此在调用beforeCreate时,为时已晚。最简单的解决方案是创建一个包含所需逻辑的User.createUser类方法:

  createUser: function(data, cb) {
    // If there are already pets specified, just use those
    if (data.pets) {return User.create(data).exec(cb);}
    // Otherwise look up the default pet
    Pet.findOne({name:"Default Pet 1"}).exec(function(err,pet) {
      // Return in case of error
      if (err) {return cb(err);}
      // Assuming the default pet exists, attach it
      if (pet) {
        console.log("SETTING DEFAULT PET", pet.id);
        data.pets = [pet.id];
      }
      // Create the pet
      return User.create(data).exec(cb);
    });
  }

一些注意事项:

  1. 在您的示例中,您将pets直接设置为ID,但由于它是一个集合,因此您必须将其设置为数组。
  2. 如果您使用的是sails-disk适配器,则需要在模型中设置schema: true才能生效。
  3. 您获取的新User模型将被填充;您必须使用find使用新的用户ID进行populate('pets')以获取附加的宠物数据。