Differences in rails between new + save and create

Solution 1:

Although it is correct that create calls new and then save there is a big difference between the two alternatives in their return values.

Save returns either true or false depending on whether the object was saved successfully to the database or not. This can then be used for flow control as per the first example in the question above.

Create will return the model regardless of whether the object was saved or not. This has implications for the code above in that the top branch of the if statement will always be executed even if the object fails validations and is not saved.

If you use create with branching logic you are at risk of silent failures which is not the case if you use new + save.

The create alternative can be useful in controllers where respond_with is used for API (JSON/XML) responses. In this case the existence of errors on the object will cause the errors to be returned in the response with a status of unprocessable_entity, which is exactly what you want from an API.

I would always use the new + save option for html, especially if you are relying on the return value for flow control.

Solution 2:

Internally create calls new then save anyway:

  def create(attributes = nil, options = {}, &block)
    if attributes.is_a?(Array)
      attributes.collect { |attr| create(attr, options, &block) }
    else
      object = new(attributes, options, &block)
      object.save
      object
    end
  end

Solution 3:

new creates the object but doesn't save it.

create creates the object and saves it, i.e. .new and .save

create! creates the object and tries to save it but raises an exception if validations fails, e.g. .new and .save!

One of confusion items is that the above is the actions that you take on an object, but similar names are also given to controller methods, especially in a RESTful environment. For example you have a create action.... which creates a new object, and then saves it and another create action which just does an object create.

If you're wondering "why create an object if I'm not going to save it?" consider this - the system 'tries' to save the object - but a validation prevents it and the user is asked to fill in more information on a form, perhaps required fields. One wants the object to still be created (.new) while this is going on and it will hold the values that have been assigned so far. However it doesn't actually get saved until it passes the validations as well.

Solution 4:

when you use, rails actually is creating the records but didn't save it, so in the process you can also assign smth

@item = Item.new(params[:item])

but when you use:

if Item.create(params[:item])
.....

it will immediately create and save

you can check it with rails c