You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
[finding] Both recorded PR-label READ legs came back label-blind in one run — pull_request_read get returned no labels field, and the web-payload grep spelling that works on issues reads zero on a labeled PR #12902
Filed unassigned, finding — an observation about the label read-before-write channel, measured in passing while landing a skip-changeset label. Not a queued defect; triage grades it.
Why this is not a duplicate
The whole-set REPLACE semantics of an agent label write are well recorded (#12553, #5649), and so is the 403 on the additive REST endpoint from a dev seat (#12654, open). Those cards all describe the WRITE. This one is about the READ that the write's own safety protocol depends on: the protocol is read current set → union with target → group write → compare read-back, and a read that returns "no labels" for a PR that HAS labels turns that protocol into a silent stripper.
#12640 recorded the first half of this and was closed with a remedy: MCP issue_read get_labels cannot resolve a PULL REQUEST number, and "the working label read for a PR is pull_request_read get". That remedy did not hold here.
Measured, 2026-08-28, on a freshly created draft PR in this repo
MCP pull_request_read method=get — succeeded, full payload (number, title, body, state, draft, merged, mergeable_state, html_url, user, head, base, additions, deletions, changed_files, commits, created_at, updated_at). It carries no labels field at all — not an empty array, absent. So the remedy [finding] MCP issue_read get_labels cannot resolve a PULL REQUEST number — the working label read for a PR is pull_request_read get #12640 was closed on returns a healthy-looking response from which a seat reads "no labels", with nothing in the response signalling that labels were never in scope. This is the dangerous direction: a successful call whose silence is indistinguishable from a real empty set.
Zero-config web payload (the public PR page) — the spelling that works on ISSUE pages is an anchor grep for href="/OWNER/REPO/labels/NAME". On a PR page that returns zero on a PR that carries labels. Applied label chips on a PR page are data-name="NAME" with the href spelled /OWNER/REPO/issues?q=state%3Aopen%20label%3ANAME. Measured: the /labels/ grep said zero; the data-name= grep on the same bytes returned documentation and size/s.
The near-miss
Following legs 1–3 as recorded, this seat computed its union as {skip-changeset} and issued the group write. The PR actually carried documentation and size/s at that moment (auto-labelers, applied within seconds of creation). Under the whole-set REPLACE semantics of #12553 that write should have stripped both.
It did not — the comparative read-back showed all three labels present, so the final state is correct and nothing was lost. But that is the write leg being kinder than its documented semantics, not the read leg working. The compare-read is what caught it; had the write behaved as #12553 records, two labels would have been dropped with the seat's own union computation reading as a clean success.
Why it is worth a card
The compare-read-back step already in the protocol is what saved this, which is evidence FOR that step. What is missing is that all three documented read legs are label-blind for a PR, two of them silently:
leg 1 fails loudly (fine — a loud failure routes around itself),
leg 2 succeeds and omits the field (silent),
leg 3 succeeds and matches nothing (silent).
A seat that takes leg 2 or leg 3 at face value computes a union that is missing every label already on the PR, on every dispatch. The correct data-name= spelling for leg 3 is measured above and is a one-line fix wherever the read spelling is recorded; whether leg 2 has a working field selector was not established here.
Suggested home
The platform-readings fact table, alongside the existing PR-body and label-write facts. ⛔ Not edited here — that file is held by open delivered PRs on this lane, which is why this is a card and not a diff.
Filed unassigned,
finding— an observation about the label read-before-write channel, measured in passing while landing askip-changesetlabel. Not a queued defect; triage grades it.Why this is not a duplicate
The whole-set REPLACE semantics of an agent label write are well recorded (#12553, #5649), and so is the 403 on the additive REST endpoint from a dev seat (#12654, open). Those cards all describe the WRITE. This one is about the READ that the write's own safety protocol depends on: the protocol is read current set → union with target → group write → compare read-back, and a read that returns "no labels" for a PR that HAS labels turns that protocol into a silent stripper.
#12640 recorded the first half of this and was closed with a remedy: MCP
issue_read get_labelscannot resolve a PULL REQUEST number, and "the working label read for a PR ispull_request_read get". That remedy did not hold here.Measured, 2026-08-28, on a freshly created draft PR in this repo
Three read legs, one PR, same minute:
MCP
issue_read method=get_labelswith the PR number —Failed to get issue labels: Could not resolve to an Issue with the number of 12901. Reproduced twice, ~2 minutes apart, so not creation-replication lag. Matches [finding] MCPissue_read get_labelscannot resolve a PULL REQUEST number — the working label read for a PR ispull_request_read get#12640.MCP
pull_request_read method=get— succeeded, full payload (number, title, body, state, draft, merged, mergeable_state, html_url, user, head, base, additions, deletions, changed_files, commits, created_at, updated_at). It carries nolabelsfield at all — not an empty array, absent. So the remedy [finding] MCPissue_read get_labelscannot resolve a PULL REQUEST number — the working label read for a PR ispull_request_read get#12640 was closed on returns a healthy-looking response from which a seat reads "no labels", with nothing in the response signalling that labels were never in scope. This is the dangerous direction: a successful call whose silence is indistinguishable from a real empty set.Zero-config web payload (the public PR page) — the spelling that works on ISSUE pages is an anchor grep for
href="/OWNER/REPO/labels/NAME". On a PR page that returns zero on a PR that carries labels. Applied label chips on a PR page aredata-name="NAME"with the href spelled/OWNER/REPO/issues?q=state%3Aopen%20label%3ANAME. Measured: the/labels/grep said zero; thedata-name=grep on the same bytes returneddocumentationandsize/s.The near-miss
Following legs 1–3 as recorded, this seat computed its union as
{skip-changeset}and issued the group write. The PR actually carrieddocumentationandsize/sat that moment (auto-labelers, applied within seconds of creation). Under the whole-set REPLACE semantics of #12553 that write should have stripped both.It did not — the comparative read-back showed all three labels present, so the final state is correct and nothing was lost. But that is the write leg being kinder than its documented semantics, not the read leg working. The compare-read is what caught it; had the write behaved as #12553 records, two labels would have been dropped with the seat's own union computation reading as a clean success.
Why it is worth a card
The compare-read-back step already in the protocol is what saved this, which is evidence FOR that step. What is missing is that all three documented read legs are label-blind for a PR, two of them silently:
A seat that takes leg 2 or leg 3 at face value computes a union that is missing every label already on the PR, on every dispatch. The correct
data-name=spelling for leg 3 is measured above and is a one-line fix wherever the read spelling is recorded; whether leg 2 has a working field selector was not established here.Suggested home
The platform-readings fact table, alongside the existing PR-body and label-write facts. ⛔ Not edited here — that file is held by open delivered PRs on this lane, which is why this is a card and not a diff.