v2.1.1
Fixes two defects where the tooling reported success it had not achieved
GitLab merges failed with 400 SHA must be provided when merging
pr_merge and pr_merge_wait were a hard block on affected GitLab projects — the MR was left open, waiting for a human, with no MCP fallback. /scpmmr completed MR-create and CI, then died at merge.
Why it started happening, and why it will keep happening: GitLab's merge endpoint rejects an unguarded merge when the project's namespace has require_sha_for_merge, and GitLab now defaults that ON for newly-created groups. This is an upstream environment change, not a regression here — which is why newly-created nested groups failed while older projects that had always merged kept working. Expect it on every new subgroup.
The adapter now resolves the MR's source-branch HEAD and passes it as --sha.
pr_status reported zero checks for PRs with passing checks
pr_status returned checks: none for GitHub PRs that had passing checks — on every GitHub PR, permanently, on any host running gh 2.45 (what Ubuntu 24.04 LTS ships). It ran gh pr checks --json, a flag that does not exist on that version, and treated the resulting non-zero exit as "no checks configured".
Checks are now read from statusCheckRollup on the existing gh pr view call — one subprocess instead of two.
Behaviour changes (not just fixes)
Both change what callers observe. Neither should break correct usage, but they are worth knowing before the upgrade.
1. --auto-merge=false is now forced on GitLab merges. A pending pipeline now merges or fails — it no longer silently enrols (merge-when-pipeline-succeeds) while the tool reports merge_method: "direct_squash" and a completed merge. Anyone who was relying on the enrolment behaviour will see a difference; that behaviour was reporting success for a non-merge.
2. pr_status now fails closed. A checks query that fails returns {ok: false, code} instead of ok: true with a zeroed summary. Callers that treated an empty summary as "this PR has no checks" will now see an error — that is the point, and it is not a regression. A genuine zero (a PR with no checks configured) still returns ok: true with summary: "none"; the two are now distinguishable.
Also in this release
-R <repo>is shell-escaped in the GitLab merge path (was the one caller-supplied field interpolated raw).- Stale-head
409handling is anchored to the HTTP status rather than a bare409match — glab echoes the request URL, which contains the MR IID, so merging MR !409 previously matched on its own number and misclassified genuine failures as races. --shaand--auto-mergeadded to the real-CLI flag-shape gate.--auto-mergeis itself a rename of the older--when-pipeline-succeeds; the mocked unit suite cannot catch a glab that rejects either flag.- Adapter errors now surface a
codethrough thepr_statushandler.
Validation
Both fixes were validated live as paired experiments — the defect reproduced first on the same fixture, then the fix applied — rather than on green unit tests alone:
- GitLab merge: reproduced
400 SHA must be provided when mergingon a realrequire_sha_for_mergenamespace, then merged. Confirmed by reading MR state back from the API, includingmerge_when_pipeline_succeeds: falseto prove a real merge rather than an armed auto-merge. pr_status:gh pr checks --jsonexits 1 on gh 2.45 (what producednone), then the new path reportedtotal 4, passed 4, all_passedon the originally-reported PR.
Full suite: 2416 tests, 0 failures, 78/78 runtime smoke, trivy 0 HIGH/CRITICAL.
Upgrade: curl -fsSL https://raw.githubusercontent.com/Wave-Engineering/mcp-server-sdlc/main/scripts/install-remote.sh | bash — then restart Claude Code so the MCP subprocess picks up the new binary.