Rails ActiveRecord::RecordInvalid exception not raised in after_create of association
<p>I have 3 very simple models</p>
<pre><code>class Receipt &lt; ActiveRecord::Base
  has_many :receipt_items
end

class ReceiptItem &lt; ActiveRecord::Base
  after_create :create_transaction
  belongs_to :receipt
private
  def create_transaction
    Transaction.new.save!
  end
end

class Transaction &lt; ActiveRecord::Base
  validates :transacted_at, :presence =&gt; true
end
</code></pre>
<p>So every time a new ReceiptItem is created, it triggers the after_create callback to create a new Transaction object using save!. But because Transaction requires that the column transacted_at to be present, Transaction.new.save! should raise an ActiveRecord::RecordInvalid every time, I assumed.</p>
<p>So then I created 3 tests:</p>
<pre><code>test &quot;creating an invalid transaction&quot; do
    assert_raises ActiveRecord::RecordInvalid do
        Transaction.new.save!
    end
end

test &quot;creating invalid transaction in after_create&quot; do
    assert_raises ActiveRecord::RecordInvalid do
        ReceiptItem.new.save!
    end
end

test &quot;creating invalid transaction in after_create of associated model&quot; do
    assert_raises ActiveRecord::RecordInvalid do
        r = Receipt.new
        i = r.receipt_items.new
        r.save!
    end
end
</code></pre>
<p>The first two tests passed as expected. The third test, however, failed because the exception was never raised. As a matter of fact, if I add the following lines after the 'r.save!' line:</p>
<pre><code>r.reload
p r.inspect
p r.receipt_items.inspect
</code></pre>
<p>I could see that the Receipt and the ReceiptItem have been created successfully.</p>
<p>Furthermore, if I replaced</p>
<pre><code>assert_raises ActiveRecord::RecordInvalid do
</code></pre>
<p>with</p>
<pre><code>assert_difference &quot;Transaction.count&quot;, +1 do
</code></pre>
<p>I confirmed that the Receipt and the ReceiptItems were created but the Transaction wasn't. That means the creation of the Transaction failed, but was silently ignored, even though I used 'save!' as opposed to just 'save'.</p>
<p>Does anyone know if this is the intended behaviour, or is this actually a bug in Rails?</p>
<p>(Tried this in Rails 4.0.13 and 4.2.0)</p>
<h3>Update</h3>
<p>I've filed a bug report here:
<a href="https://github.com/rails/rails/issues/24301" rel="nofollow noreferrer">https://github.com/rails/rails/issues/24301</a></p>