2016-01-24 8 views
10

Sto cercando di iniettare un servizio di Ember in un oggetto Ember, ma continuo a ricevere il seguente errore:Iniettare un servizio in un oggetto Ember [non è un controller Ember]

"Assertion Failed: Attempting to lookup an injected property on an 
object without a container, ensure that the object was instantiated 
via a container." 

mio codice è essenzialmente qualcosa di simile al seguente:

const Model = Ember.Object.extend({ 
    store: Ember.inject.service(), 

    destroyRecord() {...}, 

    serialize() {...}, 

    deserialize() {...}, 
}); 

let newModel = Model.create(); 
newModel.get('store'); 

Nota: funziona se iniettare il servizio in un controller, ma non un oggetto. Non ho avuto fortuna nel cercare di capire come registrare l'Oggetto con il contenitore Ember.

risposta

17

Si lavora per una Ember.Controller perché Ember controlla il ciclo di vita dell'oggetto. In breve, quando Ember ha bisogno di un'istanza di un determinato controller, richiede al contenitore uno e il contenitore fornirà l'istanza, inizializzando se necessario.

Ciò che questo implica è che per l'integrazione delle dipendenze funzioni, è necessario ottenere una nuova istanza di attraverso il contenitore. Supponendo Ember 2.3 a causa di getOwner, e che this è da qualche parte all'interno dell'applicazione Ember:

let owner = Ember.getOwner(this); 
let newModel = owner.lookup('object:model'); 
newmodel.get('store'); 

È possibile consultare il lookup documentation here.

Ma come registrarsi? Usare un inizializzatore applicazione:

$ ember generate initializer register-model 

Poi, aprire l'inizializzatore generato e, supponendo che il file è in app/folder/model.js, mettere qualcosa come:

import Model from 'app-name/folder/model'; 

export function initialize(application) { 
    application.register('object:model', Model); 
} 

export default { 
    name: 'register-model', 
    initialize 
}; 

È possibile consultare il register documentation here.

Spero che questo sia utile!

+1

Quindi, per chiarire, la registrazione di oggetti che non fanno già parte del ciclo di vita di Ember (nel mio caso, i modelli), viene eseguita con l'inizializzatore. Per recuperare la classe del modello altrove nell'app, chiama 'Ember.getOwner (this) .lookup ('object: model')', yeah? (la chiamata di ricerca apparentemente entrambi recupera la classe Model e chiama '.create()' su di essa). Nel mio caso, semplicemente importando nella parte superiore di tutti i file necessari tramite 'import Model da 'path/to/model;' ha funzionato altrettanto bene, dato che potevo ancora interagire con i metodi statici. –

+1

In breve, sì. Non hai davvero bisogno di registrarli a meno che tu non voglia che Ember gestisca il ciclo di vita, quindi "import" va bene come hai detto tu. Se vuoi discutere in modo più dettagliato, esegui il ping nel gruppo Slack! – locks

+0

in realtà, dopo aver dato un'altra occhiata, realizzo semplicemente importando tramite 'import Model da' path/to/model '; 'w/o facendo una ricerca all'interno di un oggetto già registrato tramite' Ember.getOwner (this) .lookup (...) 'solleva ancora lo stesso errore. Raggiungerò Slack una volta che avrò preso coscienza di me. –

-1

Bene, è necessario passare l'istanza del contenitore quando si crea un'istanza del modello. Il contenitore è accessibile nel percorso, controllori, componenti con this.get('controller'). AFAIK fondamentalmente qualsiasi cosa creata con il contenitore ottiene la proprietà del contenitore impostata. Ecco perché le iniezioni di servizio funzionano nei controller ecc.

Quindi, se si sta creando il modello nel metodo di una rotta. Il codice sarà simile sotto

App.IndexRoute = Ember.Route.extend({ 
    model: function() { 
    var newModel = Model.create({ 
     container: this.get('container') 
    });  
    return newModel.get('test').getText(); 
    } 
}); 

Here is a working demo.

Problemi correlati