7

我有一个主干模型:

var User = Backbone.Model.extend({
  idAttribute: '_id',

  url: '/api/user',

  defaults:
    { username: ''
    }
});

我拿它:

var user = new User();

user.fetch();

现在,作为click我的观点之一,我有这个:

toggleSubscription: function () {
  user.set('subscriptions', true);
  user.save();
}

这会导致 POST 请求。但是,该记录已经存在于服务器上,并且由于我获取了它(并且模型实例具有一个id属性),我认为 Backbone 应该执行 PUT 而不是 POST。为什么它可能会做一个 POST 呢?

4

5 回答 5

7

尝试检查user.isNew()

看起来您创建了一个没有 ID 的新模型,这就是它试图在Backbone.sync.

更新:

以上是完全正确的。之所以这样做,是POST因为它是一个新模型(这意味着它没有 id)。在获取模型之前,您需要给它一个 id。在您的示例中:

var user = new User();
user.fetch();
user.save(); // in XHR console you see POST

var user = new User({ id: 123 });
user.fetch();
user.save(); // in XHR console you see PUT
于 2012-07-20T21:37:44.667 回答
4

如果模型还没有 id,则认为它是新的。-- http://backbonejs.org/#Model-isNew

如果模型还没有 id,它被认为是新的......因此主干将发出PUT请求而不是POST.

type: 'POST'只需添加到您的保存块即可覆盖此行为:

var fooModel = new Backbone.Model({ id: 1});

fooModel.save(null, {
  type: 'POST'
});
于 2014-07-23T16:30:18.610 回答
2

使用 urlRoot 属性设置基本 URL /api/user。然后

  1. /api/user当您保存没有_id设置属性的模型时,它将发布到
  2. /api/user/{_id}当您保存具有_id属性集的模型时,它将 PUT 。请注意,它会自动将值附加_id到基本 URL。

它将查找_id属性的值,因为您已将该值设置为idAttribute.

于 2016-01-07T12:33:24.260 回答
1

服务器响应必须是这样的:

{
  _id : 111
}

因为您将 _id 设置为主键。获取模型时,验证 _id 的值,它必须有一个值:console.log(model.get('_id'));

我的想法是您在主干模型中设置了“_id”作为主键,但服务正在返回您的“id”

更新:添加正常行为的示例代码:

var UserModel = Backbone.Model.extend({
  idAttribute: '_id',

  url: '/api/user',

  defaults:
    { username: ''
    }
});
user = new UserModel({_id : 20});
user.save();
user = new UserModel();
user.save();

输出: PUT /api/user 405(方法不允许) POST /api/user 404(未找到)

检查模型的第一个实例如何具有 id 并尝试执行 PUT 但另一个 POST。我无法重现您的问题,所以我认为问题出在您的服务器响应上。

于 2012-07-20T22:39:47.687 回答
0

如果可能emulateHTTP是真的,可能值得检查。这会将您的所有 PUT 更改为 POST 并添加一个_method标题(您可能还想检查它是否存在以确认这个想法)。

于 2012-11-02T10:13:18.670 回答