Skip to content

Instantly share code, notes, and snippets.

@jameskerr
Created May 13, 2015 16:48
Show Gist options
  • Save jameskerr/69cedb2f30c95342f64a to your computer and use it in GitHub Desktop.
Save jameskerr/69cedb2f30c95342f64a to your computer and use it in GitHub Desktop.
Preview an update to a Rails Model without saving anything to the database.
# This class calls collection.build on each association that you specify in the @@variables,
# then calls assign_attributes on the attributes specific to this model.
#
# This class was created after I asked this question on stackoverflow.
# http://stackoverflow.com/questions/30109549/rails-preview-update-associations-without-saving-to-database
class PreviewEventUpdate
attr_accessor :params, :nested_params, :event
@@ids_keys = [:audience_ids, :group_ids, :location_ids, :user_ids].freeze
@@attributes_keys = [:occurrences_attributes, :ticket_types_attributes, :meta_urls_attributes].freeze
def initialize(params, event = Event.new)
@params, @event = params, event
@nested_params = {}
separate_nested_ids
separate_nested_attributes
end
def build
@event.assign_attributes(@params)
@nested_params.each do |key, attributes|
assocation_name = key.to_s.gsub(/_id|_attributes/, '').to_sym
@event.send(assocation_name).send(:build, attributes)
end
@event
end
private
def separate_nested_attributes
@@attributes_keys.each do |key|
next unless @params[key]
attributes = @params.delete(key)
@nested_params[key] = remove_destroyed_associations(attributes.values)
end
end
def separate_nested_ids
@@ids_keys.each do |key|
next unless @params[key]
@nested_params[key] = attributes_from_ids(key, @params.delete(key))
end
end
def attributes_from_ids(key, ids)
ids.reject!(&:empty?)
klass = key.to_s.split('_ids').first.classify.constantize
klass.find(ids).map(&:attributes)
end
def remove_destroyed_associations(attributes)
attributes.reject!{ |obj| obj[:_destroy] == "1" }
attributes.each { |obj| obj.delete(:_destroy) }
attributes
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment