別の解決策があります。デフォルトの Backbone.ajax 関数を、URL の配列またはハッシュをサポートする高度な jquery ajax 実行でオーバーライドします。データを並行してロードし、すべてのリクエストが完了すると制御をバックボーン モデルに戻します。
ajaxForArray = ->
options = _.first arguments
$.when.apply $, options.url.map (url) ->
$.ajax _.merge _.omit(options, ['url', 'success']), {url}
.done ->
resp =
if options.url.length > 1
_.slice(arguments).map (arg) -> _.first arg
else
_.first arguments
options.success? resp
ajaxForHash = ->
options = _.first arguments
pairs = _.transform options.url, (memo, url, key) ->
memo.push {key, url}
, []
$.when.apply $, pairs.map (pair) ->
$.ajax _.merge _.omit(options, ['url', 'success']), url: pair.url
.done ->
resp = _.slice(arguments).reduce (memo, arg, i) ->
memo[pairs[i].key] = _.first arg
memo
, {}
options.success? resp
Backbone.ajax = ->
options = _.first arguments
if _.isArray options.url
ajaxForArray.apply $, arguments
else if _.isObject(options.url) and not _.isFunction options.url
ajaxForHash.apply $, arguments
else
$.ajax.apply $, arguments
モデルは、次のように URL の配列で設定できます。
class ArrayBasedModel extends Backbone.Model
url: ['/aoo', '/boo', '/coo']
parse: (resp) ->
super _.extend {}, resp[0], resp[1], resp[2]
またはURLのハッシュ、
class HashBasedModel extends Backbone.Model
url: {aoo: '/aoo', boo: '/boo', coo: '/coo'}
parse: (resp) ->
super _.extend {}, resp.aoo, resp.boo, resp.coo
したがって、parse() がオーバーライドされた場合は、すべての ajax 呼び出しの結果をマージして Backbone.Model.parse() に渡す基本的なロジックを追加するだけです。
これにより、異なる URL のプロパティが 1 つのモデル属性で利用できるようになります。