Backbone.js:在现实世界的应用程序中呈现集合
Posted
技术标签:
【中文标题】Backbone.js:在现实世界的应用程序中呈现集合【英文标题】:Backbone.js: rendering collections in real world apps 【发布时间】:2011-11-14 02:55:06 【问题描述】:令人沮丧的是,backbone.js 应用程序的大多数“教程”示例都假定了一个干净的模型板。 IE。模型集合最初是空的,直到用户添加一个项目。当然,在现实世界的应用中情况并非如此,您通常从后端商店开始使用现有的集合。
我想知道人们如何处理骨干中的现有集合。具体来说:
在集合被fetch
ed 之后如何呈现它?是否只是遍历集合的一种情况?这应该由某些事件触发吗?
主干文档谈论“引导”,我理解这意味着使用初始加载时可用的数据(从 SEO 的角度来看,这也很有意义)。但这在实践中如何运作?数据转储到服务器端的 JS 中?还是JS检查DOM?
我觉得这是一个糟糕的问题,但我希望根据答案扩展它。
编辑
所以似乎共识是将数据作为 JS 的一方添加并在页面加载时处理。
我看到这种技术的一大缺点是搜索引擎蜘蛛无法获得该信息。从这个角度来看,从 DOM 中提取它可能会更好(尽管我还没有看到有人这样做)。或者可能添加html服务器端并将数据粘贴到JS中?
【问题讨论】:
有关使用 Backbone 引导的更多信息,请参阅官方文档:documentcloud.github.com/backbone/#FAQ-bootstrap @Rilely - 我已阅读文档。但是谢谢:) 【参考方案1】:我遇到了和你一样的情况,我并不总是希望我的数据最初被引导(特别是如果它来自第三方 api 调用)。我没有遇到任何这样做的教程,但是查看文档实际上很容易。你只需要在你的集合上绑定'reset'事件(当整个集合被重新填充时触发)并渲染。这是一个简单的例子:
my_application.js
window.MyApplication =
Models: ,
Collections: ,
Views: ,
Routers: ,
init: function()
// Start the data loading
this.someItems = new MyApplication.Collections.Items();
this.someItems.fetch();
// Start rendering the UI before the data is ready
new MyApplication.Routers.Items(this.someItems);
Backbone.history.start();
;
路由器/items_router.js
MyApplication.Routers.Items = Backbone.Router.extend(
routes:
"" : "index"
,
initialize: function(collection)
this.collection = collection;
,
index: function()
var view = new MyApplication.Views.ItemsIndex( collection: this.collection );
$('.items').html(view.render().el);
);
视图/项目/items_index.js
MyApplication.Views.ItemsIndex = Backbone.View.extend(
initialize: function()
_.bindAll(this, "render");
// Once the collection is fetched re-render the view
this.collection.bind("reset", this.render);
,
render: function()
console.log(this.collection.length);
// Render content
return this;
);
【讨论】:
【参考方案2】:就渲染集合而言,是的,我通常会遍历集合并为每个模型创建一个子视图。这是一个可能对http://liquidmedia.ca/blog/2011/02/backbone-js-part-3/有帮助的链接
你应该什么时候渲染它?嗯,这是一个很难回答的问题,但我不会说这是对任何特定事件的回应。我喜欢的一件事是我们有一个渲染子视图的主视图,该子视图渲染其他子视图。作为惯例,我们不直接渲染到 DOM,但是一旦所有的子视图都被渲染,我们将主视图附加到 DOM 并且整个页面立即显示。这避免了“无样式内容的闪烁”
关于引导,我从您阅读常见问题解答的内容中看到,这正是我在实践中所做的。我使用 ASP.Net MVC 3,所以我的服务器端渲染视图会有类似的东西(尽管我通常不会将“书籍”放在全局命名空间中):
<script type="text/javascript">
books = new BooksCollection();
books.reset(@Html.ToJson(Model));
</script>
希望对您有所帮助。
【讨论】:
我使用 ERB 或 HAML 对 Ruby on Rails 做同样的事情【参考方案3】:实际上,我在 Backbone 上做了一些工作,我发现 Bootstrapping 数据在某些情况下确实很有帮助,当您知道在页面加载时您将需要这些数据(从而减少一个额外的 AJAX 调用)
在 Symfony 中,我通过以这种方式渲染所需数据来做到这一点:
<script type="text/template" id="__user-boostrap">
% echo your data from php or render a controller in symfony or whatever server side script/framework you want %
// for example in symfony2, I do:
% render "myBundle:Core:getUser" %
</script>
现在,在 initialize() 函数中,您可以直接从 DOM 中提取这些数据,然后像往常一样开始工作:
例如,在我的路由器中,我这样做
myApp.Router = Backbone.Router.extend(
var data = JSON.parse($('__user-bootstrap').html());
var __games = new myApp.Games();
__games.reset(__games.parse(data.games));
var gameList = new myApp.GameListView( collection: __games );
$(this.gameView).html(gameList.$el);
);
希望这会有所帮助...
【讨论】:
以上是关于Backbone.js:在现实世界的应用程序中呈现集合的主要内容,如果未能解决你的问题,请参考以下文章
backbone.js - 模板不会在asp.net视图上呈现
Backbone js代码味道 - 更好的嵌入子视图的方法?