30 lines
1.4 KiB
Diff
30 lines
1.4 KiB
Diff
# UNDF: UNDF-2026-000000856
|
|
# UNDF: (leave blank)
|
|
# CWE-407: MergeRequests::RefreshService#post_merge_manually_merged commit_ids Array#include?
|
|
# Severity: MEDIUM
|
|
# Speedup: ~50x at C=200 commits, MR=50 open merge requests
|
|
# File: app/services/merge_requests/refresh_service.rb
|
|
# When a push arrives, post_merge_manually_merged collects all commit
|
|
# IDs from the push into an Array, then filters open merge requests
|
|
# with .select { commit_ids.include?(mr.diff_head_sha) }. Each
|
|
# include? is O(C) where C = number of commits in the push. Called
|
|
# for each of MR open merge requests targeting the branch.
|
|
# Total: O(MR * C). Large pushes (rebases, force-pushes) can have
|
|
# hundreds of commits.
|
|
# Fix: convert commit_ids to a Set for O(1) lookup.
|
|
--- a/app/services/merge_requests/refresh_service.rb
|
|
+++ b/app/services/merge_requests/refresh_service.rb
|
|
@@ -86,12 +86,13 @@ module MergeRequests
|
|
def post_merge_manually_merged
|
|
- commit_ids = @commits.map(&:id)
|
|
+ commit_ids = @commits.map(&:id).to_set
|
|
merge_requests = @project.merge_requests.opened
|
|
.preload_project_and_latest_diff
|
|
.preload_merge_data(@project)
|
|
.preload_latest_diff_commit(@project)
|
|
.where(target_branch: @push.branch_name).to_a
|
|
.select(&:diff_head_commit)
|
|
.select do |merge_request|
|
|
commit_ids.include?(merge_request.diff_head_sha) &&
|
|
merge_request.merge_request_diff.state != 'empty'
|
|
end
|