Foreign key populated with an object

烂漫一生 提交于 2019-12-05 02:46:34

Edit 2:

http://jsfiddle.net/2bsE9/13/

I updated the jsfiddle to reflect the changes I suggested below. As long as you are calling toJSON on your task, what gets to the server is a json object with the creator_id property set to the actual id of the user. The keyDestination here is redundant as the documentation states it is set automatically if you use keySource.

Edit:

https://github.com/PaulUithol/Backbone-relational#keysource

https://github.com/PaulUithol/Backbone-relational#keydestination

https://github.com/PaulUithol/Backbone-relational#includeinjson

The combination of the three above might solve your issue.

var Task = Backbone.RelationalModel.extend({
    relations: [
        {
            type: Backbone.HasOne,
            // The User object can be accessed under the property 'creator'
            key: 'creator',
            // The User object will be fetched using the value supplied under the property 'creator_id'
            keySource: 'creator_id',
            // The User object will be serialized to the property 'creator_id'
            keyDestination: 'creator_id',
            // Only the '_id' property of the User object will be serialized
            includeInJSON: Backbone.Model.prototype.idAttribute,


            relatedModel: User
        }
    ],
});

The documentation also states that the property specified by keySource or keyDestination should not be used by your code. The property cannot be accessed as an attribute.

Please try this and comment if that fixes your issue.

Btw, here is a nice blog post that uses backbone-relational end to end. http://antoviaque.org/docs/tutorials/backbone-relational-tutorial/

Edit

Updated jsfiddle

The problem is that Backbone-Relational explicitly deletes the keySource to 'prevent leaky abstractions'. It has a hardcoded call to unset on the attribute, in Backbone-Relational:

// Explicitly clear 'keySource', to prevent a leaky abstraction if 'keySource' differs from 'key'.
if ( this.key !== this.keySource ) {
    this.instance.unset( this.keySource, { silent: true } );
}

You will need to overwrite the unset method in your Task model:

var Task = Backbone.RelationalModel.extend({
    urlRoot: ' ',

    relations: [
        {
            type: Backbone.HasOne,
            key: 'creator',
            relatedModel: User,
            keySource: 'creator_id'
        }
    ],

    unset: function(attr, options) {
        if (attr == 'creator_id') {
          return false;
        }

        // Original unset from Backbone.Model:
        (options || (options = {})).unset = true;
        return this.set(attr, null, options);
     },

    sync: function (method, model, options) {
        options.success({
            id: 1,
            name: 'barTask',
            creator_id: 1
        });
    }
});

Obvious problems with this approach are that you will need to modify your code if either Backbone changes its Backbone.Model.unset method or Backbone-Relational changes its keySource behavior.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!