Emberjs Access a Nested Property

This question is the following of this one emberjs display an object return from an ajax call

To resume a bit, I have a dynamic list generated with some button for each item of that list. I catch the event of any button with this class :

App.EnquiriesView = Ember.View.extend({
    didInsertElement: function() {
        var that = this;

        this.$().on('click', '.view-btn', function(){
            var id = $(this).attr('data-value');
            that.get('controller').send('clickBtn', id);
        });
    }
});

And it goes to my controller here :

App.EnquiriesController = Ember.ObjectController.extend({
    actions: {
        clickBtn: function( id ) {
            console.log('DEBUG: ClickBtn OK id = ' + id);
            //console.log(App.Enquiries.findOne(id));

            this.transitionToRoute('enquiry', /*App.Enquiries.findOne(id)*/id);
        }
    }
});

The router related :

App.EnquiryRoute = Ember.Route.extend({
    model: function( param ) {
        console.log('Enquiry id = ' + param.enquiry_id);
        return App.Enquiries.findOne(param.enquiry_id);
    }
});

and my map :

App.Router.map(function() {
    this.resource('login', { path: '/' });
    this.resource('home');
    this.resource('enquiries', function (){
        this.route('create');
    });
    this.resource('enquiry', { path: 'enquiry/:enquiry_id' }, function(){
            this.route('update');
        });
});

So far for now when the user click on the button its redirect correctly to the enquiry with the good URL (e.g : /#/enquiry/1)

But the problem is coming from my update class now. I've just create a button with the action helper to display the update form :

App.EnquiryController = Ember.ObjectController.extend({
    actions: {
        update: function() {
            console.log('DEBUG: in EnquiryController update');
            console.log(this.get('model'));
            this.transitionToRoute('enquiry.update');
        }
    }
});

So when you click on the update button you are redirected to this kind of URL : /#/enquiry/undefined/update instead of /#/enquiry/1/update ...

I don't know how this can happen and how I can loose my id during the process...

Thanks for your help.

[edit] If you need to know what is my findOne function :

findOne: function(id) {
    return $.ajax({
        url: host + 'mdf/enquiry/' + id,
        type: 'GET',
        accepts: 'application/json',
        success: function (data) {
            console.log('DEBUG: GET Enquiry ' + id + ' OK');
        },
        error: function() {
            console.log('DEBUG: GET Enquiry ' + id + ' Failed');
        }
    });
}

Its fetching the data from the server for every item after you've click on the related button in the list.

Here is the object I've got back :

Object {readyState: 1, getResponseHeader: function, getAllResponseHeaders: function, setRequestHeader: function, overrideMimeType: function…}
abort: function ( statusText ) {
always: function () {
complete: function () {
done: function () {
error: function () {
fail: function () {
getAllResponseHeaders: function () {
getResponseHeader: function ( key ) {
overrideMimeType: function ( type ) {
pipe: function ( /* fnDone, fnFail, fnProgress */ ) {
progress: function () {
promise: function ( obj ) {
readyState: 4
responseJSON: Object
responseText: "{"ok":true,"enquiry":{"id":1,"domainid":"domain","userid":"userid","status":null,"type":"new","customerName":"Marco","customerEmail":"",...}"
setRequestHeader: function ( name, value ) {
state: function () {
status: 200
statusCode: function ( map ) {
statusText: "OK"
success: function () {
then: function ( /* fnDone, fnFail, fnProgress */ ) {
__proto__: Object
5

1 Answer

There's a number of issues going on here. A couple of things you're doing are very "non-ember" idiomatic, and I wouldn't be surprised if further issues pop up as a result. But I'll focus on the question asked, and if you want more advice on adjusting further segments I'm happy to provide it.

In short, you have the following code:

this.resource('enquiry', { path: 'enquiry/:enquiry_id' });

in your map, but an enquiry object that looks something like:

{"ok":true,
"enquiry":{
    "id":1,
    "domainid":"motorpark",
    "userid":"motorpark/mpuser"‌​
    ...
    }   
}

And these don't match. Your map defines that it is serialized by a field enquiry_id *which does not exist on your model. To fix this you can do one of these solutions:

Solution 1: Adjust your model

If you want to keep your map as is, you'll need to adjust your model to have an enquiry_id field, such as:

{"ok":true,
"enquiry_id":1,
"enquiry":{
    "id":1,
    "domainid":"motorpark",
    "userid":"motorpark/mpuser"‌​
    ...
    }   
}
Maya Lin-Takahashi

Maya Lin-Takahashi

Consumer Tech & Gadget Reviewer

Maya is a hardware enthusiast who tests and reviews smart home devices, smartphones, wearables, and audio gear. She focuses on practical consumer value and build quality.