0
votes

Dependency injection works fine for routes and controllers, but I am having difficulty getting it to work with custom classes. Instances of route and controller classes are automatically instantiated by Ember, which may be where the problem lies. The example below should illustrate the problem. I try to inject a session singleton in routes, controllers, and a custom model class, which extends Ember.Object. Everything works fine for routes and controllers, but it doesn't work for the custom model class.

Could the problem be that the user is created using App.User.create and is it therefore not managed by the application's container? In the console, I created an instance of App.IndexRoute and the instance did not have the session injected either. What am I overlooking here?

To be clear, I have looked at other register/inject examples (even those in Ember's source code), but it seems that I am missing a key aspect of dependency injection in Ember.

Update The example below is merely an example to illustrate the problem as one wouldn't want to inject as session singleton into every user model. The real question is how to inject a singleton object into an instance if that instance isn't created by the application's container.

App = Ember.Application.create();

App.Session = Ember.Object.extend({
  user: 'defaultUser'
});

App.User = Ember.Object.extend({
  first: '',
  last: ''
});

App.initializer({
  name: 'session',
  initialize: function(container, application) {
    application.register('session:main', App.Session);
    application.register('model:user', App.User, { singleton: false });

    application.inject('route', 'session', 'session:main');
    application.inject('controller', 'session', 'session:main');
    application.inject('model:user', 'session', 'session:main');
  }
});

App.IndexRoute = Ember.Route.extend({
  setupController: function(controller, model) {
    this._super(controller, model);

    var user = App.User.create({
      first: 'bart',
      last: 'jacobs'
    });

    console.log(this.get('session'));          // returns `session` singleton
    console.log(controller.get('session'));    // returns `session` singleton
    console.log(user.get('session'));          // returns `undefined`
  }
});
1
Singletons and Dependency Injection do not go well together.Madara's Ghost
Could you elaborate on this? The above example aims to make the session singleton accessible to every instance of the App.User class. I don't see why this should be a problem. The alternative is to have an App.Session singleton, but I prefer not to take that approach as it is considered a bad practice.Bart Jacobs
Singleton in on itself is considered a bad practice, as it hides dependencies and introduces global state and magic into your code.Madara's Ghost
That's totally an opinion, and his need of the session is a perfect example of proper singleton usage, that being said I wouldn't recommend injecting logic into your modelsKingpin2k
I completely agree and I don't intend to inject the session singleton into every user model. With the above example, I merely wanted to illustrate the problem.Bart Jacobs

1 Answers

1
votes

You are spot on, it's because you're creating the model, not the container which handles DI.