|
Ember.EditController = Ember.Mixin.create( |
|
saveError: false |
|
saveInvalid: false |
|
isEditing: false |
|
|
|
# Set associations to be associations of the content. These will then be checked for validity on save |
|
# and all of the flags, such as isDirty and isLoaded, will take these associations into consideration. |
|
# |
|
# Eg: A user may have an address model which is edited within the same transaction. |
|
# In this case you would put: |
|
# associations: ['address'] |
|
# |
|
associations: [] |
|
|
|
# Build an array of models that we will check for things such as isSaving, isLoaded, isDirty etc... |
|
models: (-> |
|
$.map($.merge(['content'], @get('associations')), (value, i) => |
|
@get(value) |
|
) |
|
).property('content', 'associations') |
|
|
|
# This will be called from the edit action, or can be called from a setupController on a route. |
|
startEdit: -> |
|
unless @get('isEditing') |
|
@set('isEditing', true) |
|
|
|
# This action exists to be called from an edit view |
|
edit: -> |
|
@startEdit() |
|
this.send('editing', @get('content')) |
|
|
|
cleanup: -> |
|
@set('isEditing', false) |
|
@set('saveError', false) |
|
@set('saveInvalid', false) |
|
@set('errors', null) |
|
if @get('isDirty') and !@get('isDeleted') |
|
@get('transaction').rollback() |
|
|
|
cancel: -> |
|
@cleanup() |
|
# Send action to the router |
|
@send("cancelled", @get('content')) |
|
|
|
resetTransaction: -> |
|
@get('models').forEach((model) => |
|
if model.get('isError') or not model.get('isValid') |
|
if model.get('id') |
|
# Horrible force the model state back to loaded.updated so it looks like an object loaded from the server |
|
# ready to be committed. |
|
model.get('stateManager').transitionTo('loaded.updated.uncommitted') |
|
else |
|
# Horrible force the model state back to created so it looks like an new object ready |
|
# to be committed again. |
|
# For some reason, model.isDirty is false now and I don't know how to get it to be dirty again. |
|
model.get('stateManager').transitionTo('loaded.created.uncommitted') |
|
) |
|
|
|
save: -> |
|
# Check before save |
|
if typeof @beforeSave == 'function' |
|
return unless @beforeSave() |
|
|
|
# Remove the errors |
|
@set('errors', []) |
|
@set('saveError', false) |
|
@set('saveInvalid', false) |
|
|
|
# Observe the record until it is finished saving |
|
@addObserver('isSaving', this, -> |
|
return if @get('isSaving') |
|
@set('saveError', @get('isError')) |
|
unless @get('isError') or @get('isInvalid') |
|
# The content is valid, we can remove the observer |
|
@removeObserver('isSaving') |
|
# If this is a new record, we want to wait until the id is populated before firing the saved event |
|
unless @get('content.id') |
|
@addObserver('content.id', this, -> |
|
# We have an id, remove the observer and fire the event |
|
@removeObserver('content.id') |
|
@set('isEditing', false) |
|
@send("saved", @get('content')) |
|
) |
|
else |
|
# This is an existing record, we can fire the saved event |
|
@set('isEditing', false) |
|
@send("saved", @get('content')) |
|
else |
|
# The record is either in error or invalid, we will reset the transaction. |
|
@removeObserver('isSaving') |
|
@resetTransaction() |
|
) |
|
# Now lets try to save |
|
@get('transaction').commit() |
|
|
|
isSaving: (-> |
|
@get('models').filterProperty('isSaving', true).get('length') > 0 |
|
).property('[email protected]') |
|
|
|
isDirty: (-> |
|
@get('models').filterProperty('isDirty', true).get('length') > 0 |
|
).property('[email protected]') |
|
|
|
isLoaded: (-> |
|
@get('models').filterProperty('isLoaded', false).get('length') == 0 |
|
).property('[email protected]') |
|
|
|
isError: (-> |
|
return false if @get('saveError') |
|
@get('models').filterProperty('isError', true).get('length') > 0 |
|
).property('[email protected]') |
|
|
|
isValid: (-> |
|
# Because we are forcing the model to become unsaved again, it clears the isValid flag. However certain |
|
# things (namely ember-bootstrap) rely on this flag to show validation errors, so if we have had an invalid |
|
# save we return false. |
|
return false if @get('saveInvalid') |
|
@get('models').filterProperty('isValid', false).get('length') == 0 |
|
).property('[email protected]') |
|
|
|
isInvalid: (-> |
|
!@get('isValid') |
|
).property('isValid') |
|
) |
|
|
|
Ember.DestroyController = Ember.Mixin.create( |
|
delete: -> |
|
@addObserver('content.isDeleted', this, -> |
|
if @get('content.isDeleted') |
|
@removeObserver('content.isDeleted') |
|
@send("deleted", @get('content')) |
|
) |
|
@get('content').deleteRecord() |
|
@get('transaction').commit() |
|
) |
We are using the latest ember data 1.0 beta and the resetTransaction method had to be modified to this. Note that their is no state manager and we don't write the entire state path