Describe the bug
When using Tableau MCP with Microsoft Copilot Studio via OAuth 2.1 Dynamic Discovery + Dynamic Client Registration (DCR), client registration succeeds, but the authorization endpoint rejects the exact same redirect URI that was previously accepted during registration.
Observed behavior:
Copilot Studio successfully discovers:
/.well-known/oauth-authorization-server
/.well-known/oauth-protected-resource
Copilot Studio successfully registers a client via:
POST /oauth2/register
Tableau MCP returns HTTP 200 and a valid client_id.
Copilot Studio calls:
GET /oauth2/authorize
using the same redirect URI that was registered.
Tableau MCP returns:
{
"error": "invalid_request",
"error_description": "Invalid redirect URI: https://global.consent.azure-apim.net/redirect/..."
}
The redirect URI used during authorization appears to be identical to the redirect URI accepted during dynamic client registration.
Expected behavior
After a successful Dynamic Client Registration request, Tableau MCP should accept the registered redirect URI during the OAuth Authorization Code flow.
Expected flow:
OAuth Discovery
↓
OAuth Protected Resource Discovery
↓
Dynamic Client Registration
↓
Authorization Request
↓
Tableau Login
↓
Authorization Code Issued
↓
Token Exchange
Actual flow stops at:
Authorization Request
↓
400 Invalid redirect URI
Versions
Tableau Server
2026.2.1
Tableau MCP Server
4.7.1
MCP Host
Microsoft Copilot Studio
Steps to reproduce
AUTH=oauth
SERVER=https://xxx.com
SITE_NAME=Default
OAUTH_ISSUER=https://.ngrok-free.app
OAUTH_RESOURCE_URI=https://.ngrok-free.app
TRANSPORT=http
OAUTH_LOCK_SITE=false
OAUTH_JWE_PRIVATE_KEY_PATH=C:\TableauMCP\keys\privkey.pem
Start Tableau MCP
npx @tableau/mcp-server
Create MCP Server in Microsoft Copilot Studio
Use OAuth 2.0 Dynamic Discovery.
Observe DCR Registration
Request:
POST /oauth2/register
Request body:
{
"redirect_uris": [
"https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
],
"token_endpoint_auth_method": "none",
"grant_types": [
"authorization_code",
"refresh_token"
],
"response_types": [
"code"
],
"client_name": "Credential Manager",
"client_uri": "https://authorization-manager.consent.azure-apim.net"
}
Response:
{
"client_id": "8bbaac4a-6df3-4810-b543-c77217e83271",
"redirect_uris": [
"https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
]
}
Observe Authorize Request
Request:
GET /oauth2/authorize
Query parameters:
client_id=8bbaac4a-6df3-4810-b543-c77217e83271
redirect_uri=https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c
response_type=code
code_challenge=
code_challenge_method=S256
Result
Response:
400 Bad Request
body
{
"error": "invalid_request",
"error_description": "Invalid redirect URI: https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
}
Logs
OAuth Authorization Server Discovery
GET /.well-known/oauth-authorization-server
Response
{
"issuer": "https://.ngrok-free.app",
"authorization_endpoint": "https://.ngrok-free.app/oauth2/authorize",
"token_endpoint": "https://.ngrok-free.app/oauth2/token",
"registration_endpoint": "https://.ngrok-free.app/oauth2/register"
}
OAuth Protected Resource
GET /.well-known/oauth-protected-resource
Response
{
"resource": "https://.ngrok-free.app/tableau-mcp",
"authorization_servers": [
"https://.ngrok-free.app"
]
}
Authorization Challenge
WWW-Authenticate: Bearer realm="MCP",
resource_metadata="https://.ngrok-free.app/.well-known/oauth-protected-resource"
ngrok Request Sequence
GET /.well-known/oauth-protected-resource 200
GET /.well-known/oauth-authorization-server 200
POST /oauth2/register 200
GET /oauth2/authorize 400
Additional Notes
The redirect URI appears to be accepted during Dynamic Client Registration but rejected during Authorization.
This was reproduced consistently using Microsoft Copilot Studio and Tableau MCP 4.7.1.
Describe the bug
When using Tableau MCP with Microsoft Copilot Studio via OAuth 2.1 Dynamic Discovery + Dynamic Client Registration (DCR), client registration succeeds, but the authorization endpoint rejects the exact same redirect URI that was previously accepted during registration.
Observed behavior:
Copilot Studio successfully discovers:
/.well-known/oauth-authorization-server
/.well-known/oauth-protected-resource
Copilot Studio successfully registers a client via:
POST /oauth2/register
Tableau MCP returns HTTP 200 and a valid client_id.
Copilot Studio calls:
GET /oauth2/authorize
using the same redirect URI that was registered.
Tableau MCP returns:
{
"error": "invalid_request",
"error_description": "Invalid redirect URI: https://global.consent.azure-apim.net/redirect/..."
}
The redirect URI used during authorization appears to be identical to the redirect URI accepted during dynamic client registration.
Expected behavior
After a successful Dynamic Client Registration request, Tableau MCP should accept the registered redirect URI during the OAuth Authorization Code flow.
Expected flow:
OAuth Discovery
↓
OAuth Protected Resource Discovery
↓
Dynamic Client Registration
↓
Authorization Request
↓
Tableau Login
↓
Authorization Code Issued
↓
Token Exchange
Actual flow stops at:
Authorization Request
↓
400 Invalid redirect URI
Versions
Tableau Server
2026.2.1
Tableau MCP Server
4.7.1
MCP Host
Microsoft Copilot Studio
Steps to reproduce
AUTH=oauth
SERVER=https://xxx.com
SITE_NAME=Default
OAUTH_ISSUER=https://.ngrok-free.app
OAUTH_RESOURCE_URI=https://.ngrok-free.app
TRANSPORT=http
OAUTH_LOCK_SITE=false
OAUTH_JWE_PRIVATE_KEY_PATH=C:\TableauMCP\keys\privkey.pem
Start Tableau MCP
npx @tableau/mcp-server
Create MCP Server in Microsoft Copilot Studio
Use OAuth 2.0 Dynamic Discovery.
Observe DCR Registration
Request:
POST /oauth2/register
Request body:
{
"redirect_uris": [
"https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
],
"token_endpoint_auth_method": "none",
"grant_types": [
"authorization_code",
"refresh_token"
],
"response_types": [
"code"
],
"client_name": "Credential Manager",
"client_uri": "https://authorization-manager.consent.azure-apim.net"
}
Response:
{
"client_id": "8bbaac4a-6df3-4810-b543-c77217e83271",
"redirect_uris": [
"https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
]
}
Observe Authorize Request
Request:
GET /oauth2/authorize
Query parameters:
client_id=8bbaac4a-6df3-4810-b543-c77217e83271
redirect_uri=https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c
response_type=code
code_challenge=
code_challenge_method=S256
Result
Response:
400 Bad Request
body
{
"error": "invalid_request",
"error_description": "Invalid redirect URI: https://global.consent.azure-apim.net/redirect/cr7c9-5fngrok-5fff0481101d9c126c"
}
Logs
OAuth Authorization Server Discovery
GET /.well-known/oauth-authorization-server
Response
{
"issuer": "https://.ngrok-free.app",
"authorization_endpoint": "https://.ngrok-free.app/oauth2/authorize",
"token_endpoint": "https://.ngrok-free.app/oauth2/token",
"registration_endpoint": "https://.ngrok-free.app/oauth2/register"
}
OAuth Protected Resource
GET /.well-known/oauth-protected-resource
Response
{
"resource": "https://.ngrok-free.app/tableau-mcp",
"authorization_servers": [
"https://.ngrok-free.app"
]
}
Authorization Challenge
WWW-Authenticate: Bearer realm="MCP",
resource_metadata="https://.ngrok-free.app/.well-known/oauth-protected-resource"
ngrok Request Sequence
GET /.well-known/oauth-protected-resource 200
GET /.well-known/oauth-authorization-server 200
POST /oauth2/register 200
GET /oauth2/authorize 400
Additional Notes
The redirect URI appears to be accepted during Dynamic Client Registration but rejected during Authorization.
This was reproduced consistently using Microsoft Copilot Studio and Tableau MCP 4.7.1.