2013-09-27 27 views
1

我與同事對路由器的責任存在分歧。我們內部單頁的應用程序,這是我印象中有網絡請求(AJAX)通過事件來處理被觸發(即Backbone.Events),像這樣:路由器是否應負責網絡請求? (Backbone.js)

events : { 
    'click a#getUsers' : 'updateModels' 
} 

updateModels: function() { 
    $.ajax(); or this.Model.fetch(); 
} 

然而,這是他了解,網絡請求應處理通過對URL更改路由器(根據點擊它的URL改變了像a[href="#getThings"]像這樣:

var App = Backbone.Router.extend({ 
    routes: { 
     "" : "main", 
     "thing" : "getThings" 
    } 

    getThings: function() { 
     this.newView = new NewView(); 
     $.ajax(); // which populates the view with data 
    } 
}); 

我想知道骨幹原因是什麼做的網絡請求

回答

2

絕大多數的你AJAX請求應以骨幹modelcollection開始,並通過backbone.sync函數處理。關鍵方法是model.fetch(),collection.fetch()model.save()

主幹是靈活的,只能處理一組非常原始的用例,所以有時候您需要跨越這些邊界,但在視圖或路由器中調用$.ajax是MVC失敗的強大代碼味道。

解決您的一些具體問題。

可以查看調用model.fetch()來加載數據嗎?

是的,這是非常好的和慣用的骨幹。

視圖能發出一個事件,最終會加載數據嗎?

是的,這是非常好的。這只是在您的應用程序複雜度增加時才調用model.fetch()而必需的,並且事件發射允許的解耦是有價值和有保證的。對於待辦事項清單,通常是矯枉過正。對於一個巨大的應用程序,這可以是一個乾淨的方法。

是否每個模型都會導致瀏覽器URL中的更改?

不,實際上很多單頁面應用程序只是永遠住在「/」處。路由到唯一的URL是可選的。有些應用程序很容易讓它自己,有些應用程序不是那麼容易。不要將「應用程序需求數據X」與「瀏覽器URL需要爲X」等同起來。這些是正交的。如果用戶在總統名單中點擊「Bill Clinton」的視圖,並且想要將URL更改爲「/ presidents/clinton」,那麼繼續並開始一條新路線,這非常合理,但有時您只是想要一些數據而不更改URL。

總結路由器的責任,我想起來了,如下所示:

  • 基於URL的圖,是應該被顯示?
  • 也基於URL,是否有需要提取並實例化到模型實例中的模型ID?
  • 線東西和渲染視圖

因此,一個典型的路由器的方法僞代碼可能是:

  • 當URL匹配/總裁/:姓名,回覆如下
  • 搶:名稱參數並製作總統模型
  • 實例化PresidentView,將其傳遞給模型
  • 調用presidentView.render()並交換視圖的元素int Ø在整體頁面佈局
+0

感謝極大幫助的解答。我知道$ .ajax()函數調用並不是最優的,但是在API中返回的json並不是最優的,因爲它返回了一些我不一定想要污染我的模型的東西。 – iggy2012

+0

我的方法是執行$ .ajax()請求,並在成功回調中實例化和設置我的模型。我的理解是Backbone.fetch()請求只是簡單地將返回的json對象轉換爲模型的一個實例,並且通常不需要返回的所有鍵/值對從API返回的JSON對象。 – iggy2012

+2

重寫模型/集合中的'parse'方法以將服務器JSON響應轉換爲主幹兼容形狀。 –

0

隨着骨幹適當的位置的DOM,你應該讓骨幹做最適合你的Ajax請求,這將是更多的,往往不是從你的觀點,而不是路由器引發的。而且,如果可以使用Backbone請求,我絕不會使用jQuery ajax請求。 this.model.fetch()是獲取模型的正確方法。我看到路由器是一種定位頁面的方式,但更細緻的細節應留給視圖。然而,在路由器中的邏輯與視圖/集合/模型中的邏輯之間的選擇比科學更具藝術性,我會看看其他主幹示例以獲得更多指導。我認爲,在很多情況下,網絡請求是在視圖中處理的,因爲它更容易。

爲了迴應您的評論,無論何時從服務器返回數據,Backbone使用解析來獲取所需的信息,因此重寫提取將是一個糟糕的決定。您可以覆蓋您的模型的分析方法以獲取所需的信息,僅此而已。即:

var YourModel = Backbone.Model.extend({ 
    parse: function(response) { 
     //You can manipulate the object in other ways as well, 
     //but here's how you'd delete info 
     delete response.junk; 
     return response; 
    } 
}); 

同樣,每次你做this.model.save()時間,它使用的toJSON()之前的模型被髮送到服務器,您也可以覆蓋:

toJSON: function() { 
    // default -> return _.clone(this.attributes); 
    return _new code here_; 
} 
+0

據我所知,this.model.fetch()對於主幹是最佳的,因爲它也自動設置模型。但是我的API設計人員並不像其他人那樣熟練(即它返回對象以及成功和失敗鍵值對之類的其他東西)。有沒有辦法來覆蓋.fetch()和.save()請求只採取我需要的? – iggy2012

+0

@ iggy2012閱讀'parse':http://documentcloud.github.io/backbone/#Model-parse –