43

同期時にモデルから特定のプロパティを除外する方法はありますか?

たとえば、あるビューステートに関するモデル情報を保持しています。ピッカーモジュールがあり、このモジュールがselectedモデルの属性を切り替えるだけだとします。後でコレクションを呼び出すときに、の値を無視して、サーバーへの同期から除外し.save()たいと思います。selected

そうするためのクリーンな方法はありますか?

詳細が必要な場合はお知らせください

4

11 に答える 11

47

これは最良の解決策のようです(@nikoshr参照質問に基づく)

Backbone.Model.extend({

    // Overwrite save function
    save: function(attrs, options) {
        options || (options = {});
        attrs || (attrs = _.clone(this.attributes));

        // Filter the data to send to the server
        delete attrs.selected;
        delete attrs.dontSync;

        options.data = JSON.stringify(attrs);

        // Proxy the call to the original save function
        return Backbone.Model.prototype.save.call(this, attrs, options);
    }
});

そのため、モデル インスタンスの保存関数を上書きしますが、必要のないデータを除外し、それを親のプロトタイプ関数にプロキシします。

于 2012-10-24T17:47:21.013 に答える
35

Underscore 1.3.3 ではpickが追加され、1.4.0 では omit が追加されましtoJSON。これは、モデルの関数をオーバーライドして属性をホワイトリストに登録する_.pickか、属性をブラックリストに登録するために非常に簡単に使用できます_.omit

またtoJSON、データをサーバーに渡すために sync コマンドで使用されるため、他の場所でこれらのフィールドを使用したくない場合、これは良い解決策だと思いますtoJSON

Backbone.Model.extend({
    blacklist: ['selected',],
    toJSON: function(options) {
        return _.omit(this.attributes, this.blacklist);
    },
});
于 2013-03-20T15:43:13.163 に答える
11

私の解決策は上記のすべてを組み合わせたものです。ブラックリストの代わりにホワイトリストを使用してください..これは一般的に良いルールです

定義

          attrWhiteList:['id','biography','status'],

そして保存を上書きします

  save: function(attrs, options) {
    options || (options = {});

 //here is whitelist or all
    if (this.attrWhiteList != null )
          // Filter the data to send to the server
             whitelisted =  _.pick(this.attributes, this.attrWhiteList);
    else  
        whitelisted =this.attributes;
    /* it seems that if you override save you lose some headers and the ajax call changes*/
    // get data
    options.data = JSON.stringify(whitelisted);

    if ((this.get('id') == 0) || (this.get('id') == null)) 
        options.type = "POST"
    else
        options.type = "PUT";


    options.contentType = "application/json";
     //        options.headers =  { 
     //            'Accept': 'application/json',
     //            'Content-Type': 'application/json' 
     //        },

    // Proxy the call to the original save function
   return  Backbone.Model.prototype.save.call(this, attrs, options);
},
于 2013-07-19T17:01:03.803 に答える
6

実際、バックボーンの保存または同期機能をいじることなくこれを達成するためのはるかに簡単な方法があります。

backbone.js の 1145 行目を見ると、

// Ensure that we have the appropriate request data.
    if (options.data == null && model && (method === 'create' || method === 'update' || method === 'patch')) {
      params.contentType = 'application/json';
      params.data = JSON.stringify(options.attrs || model.toJSON(options));
    }

これは、オプションにデータを入れることで、xhr のデータ部分をオーバーライドできることを意味します。

バックボーンの保存には model.save([attributes], [options]) が必要なので

ただし、適切な保存には id などの属性が不可欠である可能性があることを覚えておいてください

model.save( {}, { data: JSON.stringify(data) } ) ; 

だからあなたはこのようなことをしているはずです

var data = { id : model.id , otherAttributes : 'value' }  ;  
model.save( {}, { data : JSON.stringify(data) } );

これは私にとって非常にうまく機能し、フェッチ、保存、削除などのxhrを使用するバックボーンで使用できます...

于 2014-08-04T11:04:51.000 に答える
3

いくつかの回答に基づいて、これは null オブジェクトのケースと、既に設定されているcontentType場合を送信しないバックボーンの条件を説明します。options.data

EDITABLE_ATTRIBUTES = ["name", "birthdate", "favoriteFood"];

...

save: function(attrs, options) {
  // `options` is an optional argument but is always needed here
  options || (options = {});

  var allAttrs = _.extend({}, this.attributes, attrs);
  var allowedAttrs = _.pick(allAttrs, EDITABLE_ATTRIBUTES);

  // If `options.data` is set, Backbone does not attempt to infer the content
  // type and leaves it null. Set it explicitly as `application/json`.
  options.contentType = "application/json";
  options.data = JSON.stringify(allowedAttrs);

  return Backbone.Model.prototype.save.call(
    this, allowedAttrs, options);
},
于 2014-03-26T23:25:49.397 に答える
2

save使用するので、toJSONそれをオーバーライドします:

    toJSON: function(options) {
        var attr = _.clone(this.attributes);
        delete attr.selected;
        return attr;
    },

selectedただし、たとえば toJSON を使用していて、ビューが必要な場合は機能しない可能性があります。それ以外の場合は、おそらくメソッドをオーバーライドする必要がありますsave

于 2012-10-24T15:25:54.650 に答える
2

options.attrs を設定すると、API パラメータをカスタマイズできます。

var model = new Backbone.Model();
model.save(null, {
  wait: true,
  success: function() {
  },
  attrs: _.omit(model.attributes, 'selected')
});
于 2014-07-10T07:03:13.933 に答える
0

必要な値のみを設定するには、HTTP POST の代わりに HTTP PATCH を使用します。バックボーン側では、save メソッドに patch 属性を追加するだけです。

entity.save(data,{patch:true})

この属性で保存を使用すると、渡されたフィールドのみがdataサーバーに送信されます。

于 2014-08-18T13:09:52.147 に答える
0

1 回限りの場合はmode.unset('selected', { silent:true })、属性を削除するために使用できます (silent は、変更イベントの発生を回避するためだけに設定されます)。けれど。

とはいえ、上記のソリューションの1つを完全に支持します。さらに、これがより定期的に必要なものである場合。

于 2012-10-27T16:35:24.267 に答える
0

これと同じ問題があるため、役立つ小さなモジュールを作成することにしました: https://github.com/lupugabriel1/backbone-model-save

これをモデルで使用する方法は次のとおりです。

var myModel = new Backbone.ModelSave.extend({
    notSync: ['name', 'age']
});
于 2014-09-25T17:46:16.323 に答える