zdennis/activerecord-import

Model#valid? Returning True For Invalid Records After Import

Numie opened this issue · 7 comments

When I attempt to import a record that is invalid due to a uniqueness constraint, a number of ActiveModel methods are returning unexpected results. Specifically, valid? returns true after the import despite the record being invalid.

For example, I have a Post model with name and company_id attributes and a uniqueness validation like validates :name, uniqueness: { scope: :company_id }.

post = Post.first.dup
=>
#<Post:0x00007f6780ea8348
 id: nil,
 name: "Name",
 company_id: 1,
 created_at: nil,
 updated_at: nil>

post.valid?
=> false

post.new_record?
=> true

Then if I run an import, the return values change:

options = { validate: true, validate_uniqueness: true, recursive: true, all_or_none: true, track_validation_failures: true }
Post.import([post], options)
=> 
#<struct ActiveRecord::Import::Result
 failed_instances=
  [[0,
    #<Post:0x00007f6780ea8348
     id: nil,
     name: "Name",
     company_id: 1,
     created_at: nil,
     updated_at: nil>]],
 num_inserts=0,
 ids=[],
 results=[]>

post.valid?
=> true

post.new_record?
=> false

Post.new(post.attributes).valid?
=> false

I'd expect the return values of valid? and new_record? to remain the same after the import.

I'm using Rails 7.1 with Postgres.

Running in to the same problem. Using Rails 5 did you figure out a reason or fix for this ?

Running in to the same problem. Using Rails 5 did you figure out a reason or fix for this ?

No, awaiting any feedback

It seems post is being hydrated from a database record. Can you determine which record it is loading from the database by inspecting the id? I wonder if the recursive option is mistakenly populating the object from the database.

It seems post is being hydrated from a database record. Can you determine which record it is loading from the database by inspecting the id? I wonder if the recursive option is mistakenly populating the object from the database.

post.id
=> nil

So it doesn't seem like a different record is being pulled from the db. Somehow valid? is being overwritten to make a non-persisted and invalid record return true?

Strange, I wonder why new_record? is returning false.

have you tried adding raise_error ?? i tried it and the it showed the error for me.
on my case the company is new and not saved yet, the post.valid? was returning true for me because it was actually valid if i just use post.save! it will also save the company first then save the post.

No, I don't want to raise errors, otherwise import! could be used. I just want methods like valid? to return false correctly if the import is unsuccessful.