Preload merge request authors for project pipelines
What does this MR do and why?
The ProjectPipelines GraphQL query runs more users queries as the number of merge request authors grows. This MR preloads the author and target project of each merge request, so the query count no longer depends on the authors.
- The lookahead preload for the
mergeRequestfield inResolvers::Ci::ProjectPipelinesResolvernow loads{ merge_request: [:author, :target_project] }instead of only:merge_request. - This is the same pair the merge request GraphQL resolvers (
MergeRequests::LookAheadPreloads#unconditional_includes) and the REST user pipelines API (Ci::Pipeline.with_user_pipelines_api_associations) already preload. - A new request spec example adds two merge request pipelines with different authors.
- No feature flag: it is a plain preload of existing associations that REST already uses.
- No database review needed: these are primary-key
INlookups onusersandprojects.
Before the change, adding two merge request pipelines with new authors went from 40 to 44 queries in that spec (cached queries included). After it, the count stays the same.
A separate MR batches the jobs of CI stages for the same query.
Why this happens and how it was measured
- The external
ProjectPipelinesquery on GitLab.com selectsmergeRequest { iid }on every node ofproject.pipelines. It had 120,296 requests on 2026-09-16, with p95 at 319 queries on the main replica. MergeRequestTypeauthorizes each merge request withread_merge_request.MergeRequestPolicyprevents it for hidden merge requests.MergeRequest#hidden?readsauthor&.banned?, so the policy loads each author. The policy subject is the merge request'starget_project.- The resolver preloaded only
merge_request. So each distinct author cost oneusersquery, and each merge request one (SQL-cached)projectslookup. - The existing N+1 shared example for merge request fields did not catch this. All its merge requests share the factory default author (the project creator).
- Measured in the new spec, with cached queries included: 40 queries before adding two merge request pipelines with new authors, 44 after, without the fix. With the fix the count stays the same.
References
Screenshots or screen recordings
This does not apply. The change is backend-only and has no UI change.
How to set up and validate locally
-
Open GraphiQL at
/-/graphql-exploreron a project with several merge request pipelines whose merge requests have different authors. -
Run this query, replacing the project path:
query { project(fullPath: "<project path>") { pipelines(first: 20) { nodes { id mergeRequest { iid } } } } } -
Open the performance bar and check the
usersqueries for the request. -
Confirm the number of
usersqueries does not grow with the number of merge request authors.
MR acceptance checklist
Evaluate this MR against the MR acceptance checklist. It helps you analyze changes to reduce risks in quality, performance, reliability, security, and maintainability.