2014-10-09 2 views
0

В Ember, когда модель доступна для контроллера?Ember.js: Когда модель доступна для контроллера?

Ниже приведено простое приложение Ember со статической моделью и контроллером, пытающимся получить доступ к модели на init. Вы заметите, что на init атрибутом модели title является undefined. Тем не менее, setTimeout показывает, что model позже доступен.

У меня создалось впечатление, что Эмбер не будет инициировать контроллер, пока модель не будет готова. Это верно? Документация Ember (http://emberjs.com/guides/routing/specifying-a-routes-model/) указывает, что модели, даже если они загружаются асинхронно, доступны при создании экземпляра контроллера.

http://jsfiddle.net/vu263uwq/1/

App = Ember.Application.create({}); 

App.IndexRoute = Ember.Route.extend({ 
    model: function() { 
     return posts[0]; 
    } 
}); 

App.IndexController = Ember.ObjectController.extend({ 
    alertTitle: function() { 
     var that = this; 

     jQuery(".output").append("1. "+this.get("title")+"<br />"); //Returns "undefined" 

     setTimeout(function() { 
      jQuery(".output").append("2. "+that.get("title")); //Returns the correct title 
     }, 1000); 
    }.on("init") 
}); 

var posts = [ 
    { 
     id: 1, 
     title: "First title", 
     body: "Cras mattis consectetur purus sit amet fermentum. Fusce dapibus, tellus ac cursus commodo, tortor mauris condimentum nibh, ut fermentum massa justo sit amet risus. Nullam quis risus eget urna mollis ornare vel eu leo. Cras justo odio, dapibus ac facilisis in, egestas eget quam." 
    },{ 
     id: 2, 
     title: "Second title", 
     body: "Maecenas faucibus mollis interdum. Vestibulum id ligula porta felis euismod semper. Cras justo odio, dapibus ac facilisis in, egestas eget quam. Fusce dapibus, tellus ac cursus commodo, tortor mauris condimentum nibh, ut fermentum massa justo sit amet risus. Aenean eu leo quam. Pellentesque ornare sem lacinia quam venenatis vestibulum." 
    } 
]; 

ответ

2

Ваше впечатление на самом деле не так. Ключ setupController - это то, где вы устанавливаете любые свойства на контроллере, включая модель. Фактически, все setupController по умолчанию задает модель на контроллере. Вот почему, если вы переопределяете крючок и все еще нуждаетесь в наборе model, вы должны явно установить модель или позвонить в this._super(controller, model).

Обратите внимание на подпись для setupController:

setupController: function(controller, model) 

Для того, чтобы это работало, контроллер уже должен быть реализован в точке, где Эмбер устанавливает модель. Инициатор запускается во время создания контроллера. Таким образом, вызов init происходит перед model является set`

Что касается асинхронной выборки моделей, если ваша модель крюк возвращает обещание, Эмбер будет блокировать до тех пор, выполнили обещание не может быть передано в функцию setupController так, что модель возлагается на выполнение обещания, а не на само обещание. Это позволяет избежать звонков, как:

setupController: function(controller, model){ 
    var self = this; 
    makeAsyncCallReturningPromise().then(function(result){ 
     self._super(controller, result); 
    } 
} 

, который будет в основном сделать то же самое

+0

https://github.com/emberjs/ember.js/blob/master/packages/ember-routing/lib/ system/route.js # L981 - это место, где создается экземпляр контроллера. :) – Microfed

+0

@Microfed ах, я исправил свой пост. Я имел в виду, что init вызывается, когда создается экземпляр контроллера, который происходит перед вызовом 'this.setupController (контроллер, контекст, переход);' – sunrize920

+0

@ sunrize920 Есть ли событие, которое вызовет функцию внутри контроллера, когда модель доступен? Например, '.on (« ready »)' или что-то в этом роде? Есть ли причина, по которой контроллер создается до того, как модель будет доступна? Кажется странным, поскольку от него зависит Контролер. Просто любопытно. – Jason

Смежные вопросы