Fix group vulnerability export segment boundaries
What does this MR do and why?
Since !253454 (merged) (b87a93e1, "Speed up filtered vulnerability CSV export enqueue"), group-level vulnerability CSV exports fail: Gitlab::Export::SegmentedExportWorker raises ActiveRecord::RecordNotFound: Couldn't find Vulnerabilities::Read with 'vulnerability_id'=<id> in ExportService#export_segment, the export is marked failed, and the user never gets the "export ready" email.
Root cause: enqueue_segmented_export now stores part boundaries with records.first[boundary_column], where boundary_column was :id for groups. Vulnerabilities::Read uses vulnerability_id as its primary key, and record[:id] reads the raw vulnerability_reads.id column rather than the primary key (before !253454 (merged) the code used records.first.id, which returns the primary key). export_segment then looks the boundaries up with Vulnerabilities::Read.find, by vulnerability_id, so it raises RecordNotFound whenever the two ids differ, which is true for nearly all real data. The group keyset scopes (in_parent_group_after_and_including / before_and_including) also compare on the primary key.
Fix: store vulnerability_id boundaries for groups too, which is what export_segment and the keyset scopes expect. The now-unneeded boundary_column helper is removed. Project exports are unchanged: they already bounded on vulnerability_id, and the narrowed select from !253454 (merged) is kept.
Specs:
- The shared
segmented export behaviourexample expected group parts to use the read'sid, encoding the bug. It now expectsvulnerability_idfor both groups and projects. - New regression test: a group export where
vulnerability_reads.iddiffers fromvulnerability_idenqueues parts thatexport_segmentcan generate. It raisesRecordNotFoundwithout this fix.
References
Closes #631098
Regression from !253454 (merged).
How to set up and validate locally
- In a group whose
vulnerability_reads.idvalues differ from theirvulnerability_id(for example, runVulnerabilities::Read.where(project: <project>).update_all('id = id + 1000000')in a Rails console on GDK). - Request a group vulnerability export from Secure > Vulnerability report > Export.
- Before:
SegmentedExportWorkerfails withRecordNotFoundand no email is sent. After: the export completes and the email arrives.
Specs:
bundle exec rspec ee/spec/services/vulnerability_exports/export_service_spec.rbMR acceptance checklist
Evaluate this MR against the MR acceptance checklist.