简体   繁体   中英

EmberJS set defaultValue from parent's model

I need to set defaultValue of price attribute to the price of item. I don't want use ComputedProperty because when my item's price is change, my transaction_detail's price is changed too, and my scenario is set price value on the first time & shouldn't changed.

Here is my TransactionDetail.js.

var TransactionDetail = DS.Model.extend({
  transaction: DS.belongsTo('transaction'),
  item: DS.belongsTo('item', { async: true }),
  borrowed_at: borrowedAt,
  max_returned_at: maxReturnedAt,
  returned_at: DS.attr('date'),
  price: DS.attr('number', {
    defaultValue: function( detail) {
      return detail.get('item.price'); // EXPECT TO GET ITEM'S PRICE, BUT ACTUAL IS NULL
    }
  }),
});

And below is my Item.js

var Item = DS.Model.extend({
  name: DS.attr('string'),
  is_available: DS.attr('boolean', { defaultValue: true }),
  price: DS.attr('number', { defaultValue: 0 })
});

UPDATE: After I read this , I add file on initializers/reopen-store.js and edit content as below:

import DS from 'ember-data';

export function initialize(container, application) {
  var store = container.lookup('store:main');

  store.reopen({
    createRecord: function(type, properties) {
      if (type === 'transactionDetail') {
        if (typeof properties.price !== 'number') {
          properties.price = properties.item.get('price');
        }
      }

      return this._super.apply(this, arguments);
    }.on('createRecord')
  });

};

export default DS.Store.extend({
  name: 'reopen-store',
  initialize: initialize
});

but when I do debugger; on model, this.get('item.price') still undefined . Any idea?

UPDATE 2:

Thanks GJK for your response. But your answer still no luck for me. Here is my app/store.js :

import DS from 'ember-data';

export default DS.Store.extend({
    init: function() {
        console.log('Init called!');
        return this._super.apply(this, arguments);
    },
    createRecord: function(type, properties) {
      console.log('Prepare createRecord!');
      debugger;

      if (type === 'transactionDetail') {
        if (typeof properties.price !== 'number') {
          properties.price = properties.item.get('price');
        }
      }

      return this._super.apply(this, arguments);
    }
});

In my console, the output just Init called! . No 'Prepare createRecord!' and debugger is not triggered in my Chrome. Any idea?

In your defaultValue function, item.price is coming up null because the item relationship likely hasn't been initialized yet. Personally, I would take care of this in the store when you create the record, not in the model.

App.Store = DS.Store.extend({
    createRecord: function(type, properties) {
        if (type === 'transactionDetail') {
            if (typeof properties.price !== 'number') {
                properties.price = properties.item.get('price');
            }
        }

        return this._super.apply(this, arguments);
    }
});

A bit more error checking is probably required, but you get the idea. If the price isn't given at the time of creation, fill it in and let the store handle the rest.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM