When upsert records with upsert_all method on AR 7.0 above, Paranoia restore any matching deleted record.
The sql from AR 6 returned something like this if we do an upsert from the added test:
INSERT INTO \"employers\" (\"id\",\"name\") VALUES (1, 'new_e1'), (2, 'new_e2') ON CONFLICT (\"id\") DO UPDATE SET \"name\"=excluded.\"name\"
With AR 7, InsertAll includes scope keys automatically, generates sql into something like this:
INSERT INTO \"employers\" (\"id\",\"name\",\"deleted_at\") VALUES (1, 'new_e1', NULL), (2, 'new_e2', NULL) ON CONFLICT (\"id\") DO UPDATE SET \"name\"=excluded.\"name\",\"deleted_at\"=excluded.\"deleted_at\" RETURNING \"id\"
How to reproduce:
use this test, it will fail on AR 7.0+
def test_upsert_all_on_soft_deleted_record
e1 = Employer.create(name: "e1")
e2 = Employer.create(name: "e2", deleted_at: Time.current)
assert_nil e1.deleted_at
assert e2.deleted_at != nil
Employer.upsert_all([
{ id: e1.id, name: "new_e1" },
{ id: e2.id, name: "new_e2" }
])
assert e1.reload.name == "new_e1"
assert e2.reload.name == "new_e2"
assert_nil e1.reload.deleted_at
assert e2.reload.deleted_at != nil
end
When upsert records with
upsert_allmethod on AR 7.0 above, Paranoia restore any matching deleted record.The sql from AR 6 returned something like this if we do an upsert from the added test:
With AR 7, InsertAll includes scope keys automatically, generates sql into something like this:
How to reproduce:
use this test, it will fail on AR 7.0+