Files
coder/coderd
Garrett Delfosse 50f36315fd fix(coderd): accept RFC 9728 resource metadata with array-valued resource (#28592)
GitLab's official MCP server returns `"resource"` as a JSON array in its
`/.well-known/oauth-protected-resource` document, while RFC 9728 §2
defines it as a string. Coder's OAuth2 auto-discovery failed to decode
the response (`json: cannot unmarshal array into Go struct field
protectedResourceMetadata.resource of type string`), blocking
zero-config `oauth2` DCR against GitLab.

This makes `protectedResourceMetadata.Resource` tolerate both a single
string and an array of strings.

Part of
[CODAGT-570](https://linear.app/codercom/issue/CODAGT-570/coder-agents-mcp-client-cannot-connect-to-gitlabs-official-mcp-server).
The other blocker in that issue (GitLab replying 204 to
`notifications/initialized`) was already fixed by the migration from
`mark3labs/mcp-go` to `modelcontextprotocol/go-sdk`, whose
streamable-HTTP client accepts 204.

<details>
<summary>Investigation notes</summary>

CODAGT-570 reported two independent incompatibilities with GitLab CE's
`/api/v4/mcp` server:

1. **204 vs 202 on `notifications/initialized` (blocked all auth
modes):** the bundled `mark3labs/mcp-go` client only accepted 200/202
for notification POSTs. That library has since been removed entirely;
`coderd/x/chatd/mcpclient` now uses
`github.com/modelcontextprotocol/go-sdk v1.7.0`, which accepts both 204
and 202 (and only warns on other codes in non-strict mode, which is the
only mode reachable from Coder). No further change needed.
2. **RFC 9728 `resource` array (blocked zero-config oauth2 DCR):**
Coder's own parser in `coderd/mcp.go` declared `Resource string`. This
lives outside the MCP library, so the SDK migration did not fix it.
Fixed here with a custom `UnmarshalJSON` accepting string or array of
strings. The field is only decoded, never consumed downstream, so
behavior is otherwise unchanged.

</details>

---

Generated by Coder Agents on behalf of @f0ssel.
2026-08-26 12:27:17 -04:00
..