Set project_id on diff files before bulk insert during import

What does this MR do and why?

During project import, MergeRequestDiffFile objects are bulk inserted via BulkInsertableAssociations. This concern only sets the foreign key (merge_request_diff_id) but not the project_id column.

When merge_request_diff_files is partitioned by merge_request_diff_id with a NOT NULL constraint on project_id, the bulk insert fails because project_id is nil.

This MR adds a before_save callback on MergeRequestDiff that propagates its project_id to all associated diff files before they are bulk inserted.

Root cause

  1. MergeRequestDiffFile has a before_validation :update_project_id callback
  2. But BulkInsertableAssociations calls bulk_insert! with validate: false
  3. So the callback never runs and project_id stays nil
  4. The NOT NULL constraint (added for partitioning) then fails

Fix

Add before_save :ensure_diff_files_project_id to MergeRequestDiff which iterates over the in-memory diff files and sets their project_id from the parent before bulk insert.

Fixes import failures that would occur after !241924 (merged) is merged.

MR acceptance checklist

Please evaluate this MR against the MR acceptance checklist. It helps you analyze changes to reduce risks in quality, performance, reliability, security, and maintainability.

How to set up and validate locally

  1. Apply the partitioning changes from !241924 (merged) (or wait for it to merge)
  2. Run RAILS_ENV=test bin/rails db:reset to pick up the partitioned schema
  3. Run bundle exec rspec spec/lib/gitlab/import_export/project/tree_restorer_spec.rb
  4. Without this fix: 35 failures with PG::CheckViolation: check constraint "check_87c184d62f"
  5. With this fix: All 192 tests pass

Merge request reports

Loading
Loading