fix: move audience mapper from scope to nextcloud-mcp-server client
The token-exchange-nextcloud scope was being inherited by DCR clients and requested by external MCP clients (like Gemini CLI), causing all tokens to have aud: "nextcloud" even when targeting the MCP server. ## Problem When external clients registered via DCR, they inherited all optional scopes from the realm defaults, including token-exchange-nextcloud. When these clients requested tokens, they would include this scope, which added aud: "nextcloud" via the scope's protocol mapper. This caused authentication failures for MCP server access: ``` 'aud': 'nextcloud' WARNING - Token rejected: wrong audience ['nextcloud'], expected nextcloud-mcp-server ``` ## Root Cause Client scopes with protocol mappers are applied whenever that scope is requested, regardless of which client requests it. The token-exchange-nextcloud scope was designed for the MCP server's own token requests to Nextcloud APIs, but external clients were also requesting it. ## Solution Move the audience mapper from the token-exchange-nextcloud scope to a direct protocol mapper on the nextcloud-mcp-server client itself. ### Changes 1. **Remove token-exchange-nextcloud from nextcloud-mcp-server optional scopes** - External DCR clients won't inherit this scope - Prevents external clients from requesting it 2. **Add nextcloud-audience protocol mapper directly to nextcloud-mcp-server** - Hardcode aud: "nextcloud" for this client only - Only tokens issued TO nextcloud-mcp-server will have this audience - External MCP clients won't be affected ## Behavior After Fix **Gemini CLI (DCR client) → MCP Server**: - Client doesn't have token-exchange-nextcloud scope - Token audience: Based on RFC 8707 resource parameter (if provided) - Result: No hardcoded audience ✅ **MCP Server (nextcloud-mcp-server) → Nextcloud APIs**: - Client has nextcloud-audience protocol mapper - Token audience: Always "nextcloud" (hardcoded) - Result: aud: "nextcloud" for Nextcloud API access ✅ ## Related - RFC 8707: Resource Indicators for OAuth 2.0 - Keycloak client scopes vs. client protocol mappers - DCR client scope inheritance 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -229,6 +229,18 @@
|
||||
"fullScopeAllowed": true,
|
||||
"nodeReRegistrationTimeout": -1,
|
||||
"protocolMappers": [
|
||||
{
|
||||
"name": "nextcloud-audience",
|
||||
"protocol": "openid-connect",
|
||||
"protocolMapper": "oidc-audience-mapper",
|
||||
"consentRequired": false,
|
||||
"config": {
|
||||
"included.client.audience": "nextcloud",
|
||||
"access.token.claim": "true",
|
||||
"id.token.claim": "false",
|
||||
"introspection.token.claim": "true"
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "sub",
|
||||
"protocol": "openid-connect",
|
||||
@@ -308,7 +320,6 @@
|
||||
"phone",
|
||||
"offline_access",
|
||||
"microprofile-jwt",
|
||||
"token-exchange-nextcloud",
|
||||
"notes:read",
|
||||
"notes:write",
|
||||
"calendar:read",
|
||||
|
||||
Reference in New Issue
Block a user