Skip to content

fix(api): populate PullRequestStatus so apply requirements are evaluated#6535

Merged
chenrui333 merged 8 commits into
runatlantis:mainfrom
gBarczyszyn:fix/api-populate-pull-request-status
Jun 25, 2026
Merged

fix(api): populate PullRequestStatus so apply requirements are evaluated#6535
chenrui333 merged 8 commits into
runatlantis:mainfrom
gBarczyszyn:fix/api-populate-pull-request-status

Conversation

@gBarczyszyn

@gBarczyszyn gBarczyszyn commented May 28, 2026

Copy link
Copy Markdown
Contributor

Fixes #6534

Problem

POST /api/plan and POST /api/apply always fail with Pull request must be mergeable before running … (or the equivalent for approved) when the target repo configures apply_requirements: [mergeable] or [approved], even when the PR is in fact mergeable/approved on the VCS side.

Root cause

APIController.apiParseAndValidate builds a synthetic command.Context from the JSON body but never populates command.Context.PullRequestStatus. That zero value is propagated to every command.ProjectContext.PullReqStatus by ProjectCommandContextBuilder, so the checks in server/events/command_requirement_handler.go:

case raw.MergeableRequirement:
    if !ctx.PullReqStatus.MergeableStatus.IsMergeable { … }
case raw.ApprovedRequirement:
    if !ctx.PullReqStatus.ApprovalStatus.IsApproved { … }

read IsMergeable=false / IsApproved=false and reject the command unconditionally. The comment-driven runners do not have this issue because PlanCommandRunner / ApplyCommandRunner explicitly call pullReqStatusFetcher.FetchPullStatus(ctx.Log, pull) and assign the result before building project commands.

Change

  • Add an optional PullReqStatusFetcher vcs.PullReqStatusFetcher field on APIController (no validate:"required" tag — existing direct callers still compile).
  • In apiParseAndValidate, when request.PR > 0 and the fetcher is wired, call FetchPullStatus(logger, pull) and assign the result to ctx.PullRequestStatus before returning the context.
  • Wire the existing pullReqStatusFetcher from server.go into APIController. The same fetcher already drives the comment flow, so no new dependency is introduced.
  • Two unit tests using the generated MockPullReqStatusFetcher:
    • TestAPIController_PlanFetchesPullReqStatus — when PR > 0, fetcher is called exactly once.
    • TestAPIController_PlanSkipsPullReqStatusWhenNoPR — when PR is omitted, fetcher is never called (zero-PR callers keep their previous behavior).

Because PullReqStatus carries both MergeableStatus and ApprovalStatus, this single change unblocks both mergeable and approved requirements via the API.

Validation

  • go test ./server/controllers/... ./server/... passes locally.
  • go vet clean.
  • Manually validated end-to-end against a real deployment: prior to the fix, /api/apply (and the equivalent MCP write tool I'm running on a fork) was returning the mergeable failure for a PR that GitHub reported as MERGEABLE. With this fix, the requirement is evaluated against actual VCS state, terraform apply runs to completion when the PR meets the requirements, and is properly rejected when it does not.

Backwards compatibility

The new field is optional. If it isn't wired (e.g. in third-party code constructing APIController directly), behavior is exactly as before. PR=0 requests also skip the fetch, matching existing behavior for branch-only API calls.


I'm happy to iterate on naming or split tests differently if you'd prefer. Thanks for taking a look!


Developed with assistance from Claude Opus 4.7 via Claude Code.

The synthetic command.Context built in APIController.apiParseAndValidate
never set PullRequestStatus, so MergeableRequirement and ApprovedRequirement
always read the zero value and rejected every API plan/apply against repos
that listed those requirements in apply_requirements.

Inject vcs.PullReqStatusFetcher into APIController and, when the request
includes a real PR number, populate ctx.PullRequestStatus before returning
the context. This mirrors how PlanCommandRunner and ApplyCommandRunner
already handle the same field for the comment-driven flow. The field is
optional, so existing callers (including tests) keep compiling unchanged.

Fixes runatlantis#6534

Assisted-by: Claude <noreply@anthropic.com>
Signed-off-by: Guilherme Barczyszyn <guilherme.barczyszyn@maistodos.com.br>
Copilot AI review requested due to automatic review settings May 28, 2026 14:27
@dosubot dosubot Bot added bug Something isn't working go Pull requests that update Go code labels May 28, 2026
@Kryan90

Kryan90 commented Jun 19, 2026

Copy link
Copy Markdown

Any chance of this PR landing? "mergeable" check seems to be entirely broken currently

@chenrui333

Copy link
Copy Markdown
Member

Any chance of this PR landing? "mergeable" check seems to be entirely broken currently

it would happen today

Keep PR-backed API plan/apply requests running when the optional pull request status lookup fails, matching the comment-runner behavior of warning and continuing with zero-valued status.

Assisted-by: OpenAI <noreply@openai.com>
Signed-off-by: Rui Chen <rui@chenrui.dev>
Refresh PR status after the API apply endpoint runs its built-in plan phase so mergeable and approved requirements use the VCS state produced by that plan.

Assisted-by: OpenAI <noreply@openai.com>
Signed-off-by: Rui Chen <rui@chenrui.dev>
Reset cached pull request status when a status refresh fails so API apply requirements cannot reuse stale pre-plan mergeability or approval state.

Assisted-by: OpenAI <noreply@openai.com>
Signed-off-by: Rui Chen <rui@chenrui.dev>
@dosubot dosubot Bot added the lgtm This PR has been approved by a maintainer label Jun 25, 2026
@chenrui333

Copy link
Copy Markdown
Member

@gBarczyszyn thanks for your first contribution to atlantis!

@chenrui333 chenrui333 merged commit e017fb6 into runatlantis:main Jun 25, 2026
42 checks passed
chenrui333 added a commit that referenced this pull request Jun 25, 2026
Follow-up to #6498, #6543, #6568, #6557, #6533, #6535, #6570, #6541, and #6554.

Assisted-by: OpenAI <noreply@openai.com>
Signed-off-by: Rui Chen <rui@chenrui.dev>
chenrui333 added a commit that referenced this pull request Jun 25, 2026
Follow-up to #6498, #6543, #6568, #6557, #6533, #6535, #6570, #6541, and #6554.

Assisted-by: OpenAI <noreply@openai.com>
Signed-off-by: Rui Chen <rui@chenrui.dev>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working go Pull requests that update Go code lgtm This PR has been approved by a maintainer

Projects

None yet

Development

Successfully merging this pull request may close these issues.

API/apply: PullRequestStatus is never populated, so mergeable requirement always fails

3 participants