- 6 minutes to read

Nodinite MCP Endpoint External Access

This guide explains how to expose the Nodinite MCP Endpoint for remote MCP clients with a secure, standards-aligned OAuth flow. It targets administrators who need reliable external connectivity from Visual Studio Code and similar MCP-capable tools.

  • Use one canonical URL across IIS, MCP settings, Web Client settings, and MCP clients
  • Use OAuth 2.0 and JWT Bearer for remote MCP clients
  • Keep database access server-side so clients only present OAuth tokens
  • Validate deployment quickly with deterministic metadata checks

What Is the Nodinite MCP Endpoint?

The Nodinite MCP Server exposes repository, monitoring, and documentation data through the open Model Context Protocol (MCP) so AI clients can query live environment data with read-only tools.

  • Transport is Streamable HTTP at /mcp.
  • The server hosts as an ASP.NET Core site (commonly in IIS like other core services).
  • Clients receive OAuth tokens, not database connection strings.
  • A --stdio mode exists for local development, but this page focuses on external HTTP access.

Authentication Model

At startup, the server chooses exactly one authentication mode:

Mode When it is used Suitable for
OAuth 2.0 / JWT Bearer Identity provider discovery endpoint is configured Remote MCP clients such as Visual Studio Code and AI assistants
Windows (Negotiate) No identity provider configured Same-domain, non-MCP-standard clients
None --stdio Local development

Remote MCP clients follow standard MCP discovery:

  1. Client calls /mcp.
  2. Server returns 401 and points to /.well-known/oauth-protected-resource.
  3. Client reads authorization server and scope metadata.
  4. User signs in.
  5. Client retries with a Bearer token.

Windows authentication does not satisfy this MCP OAuth handshake for remote clients. Use OAuth mode for external access.

Understanding External Access Flow

graph LR Client["fa:fa-laptop-code MCP client"] --> Endpoint["fa:fa-plug https://mcp.example.com:44005/mcp"] Endpoint --> Metadata["fa:fa-file-lines /.well-known/oauth-protected-resource"] Metadata --> Entra["fab:fa-microsoft Microsoft Entra ID"] Entra --> Token["fa:fa-key OAuth Bearer token"] Token --> Endpoint Endpoint --> Data["fa:fa-database Nodinite repository and monitoring data"]

Diagram: External MCP clients discover OAuth metadata, authenticate against Microsoft Entra ID, and then call the canonical MCP endpoint with Bearer tokens to query Nodinite data safely over HTTPS.

Pick one exact public URL and use it everywhere, for example https://mcp.example.com:44005/mcp.

Use the same URL in these locations:

  1. IIS binding (host name, port, certificate)
  2. Mcp:ResourceUrl in MCP server appsettings.json
  3. Web Client Services configuration when AI Assistant MCP tools are used
  4. Every MCP client configuration

Warning

MCP clients validate the advertised resource value against the actual connection URL. Any mismatch in scheme, host, or port can make a standards-compliant client reject the server.

External Access Requirements

  • DNS name resolves from every client location
  • Publicly trusted TLS certificate for the chosen name
  • Chosen port open on server firewall, cloud NSG/security group, and client-side egress path
  • If a proxy/CDN fronts DNS, ensure the selected port is actually forwarded

Step 2 - Register the MCP API in Microsoft Entra ID

Create one app registration for the MCP API, for example nodinite-mcp-server.

Create the application

  1. Open App registrations and create a single-tenant app.
  2. Record Application (client) ID as <mcp-api-app-id>.
  3. Record Directory (tenant) ID as <tenant-id>.

Expose API scopes

Set Application ID URI to api://<mcp-api-app-id> and add delegated scopes:

Scope Grants access to
mcp:repository.read Systems, Services, EndPoints, Message Types, Contracts, Custom Fields, Custom Metadata, Articles, Domains, BPMs, Resources, Categories, Applications
mcp:integrations.read Integrations
mcp:monitorviews.read Monitor Views
mcp:monitoragents.read Sources (monitor agents)
mcp:logviews.read Log Views

Pre-authorize clients when possible

Add authorized client applications for MCP clients you want to connect without consent prompts.

For Visual Studio Code, add the published client ID:

aebc6443-996d-45c2-90f0-388ff96faa56

Select all five mcp:* scopes.

Set token version

In the Entra app manifest, set requestedAccessTokenVersion to 2.

Step 3 - Configure the MCP Server

Configure the MCP server appsettings.json and recycle the site after updates.

{
  "services": {
    "identity-provider-discovery-endpoint": {
      "http": {
        "0": "https://login.microsoftonline.com/<tenant-id>/v2.0/.well-known/openid-configuration"
      }
    }
  },
  "Mcp": {
    "ResourceUrl": "https://mcp.example.com:44005/mcp"
  },
  "Authentication": {
    "RequireHttpsMetadata": true,
    "Audiences": [
      "<mcp-api-app-id>",
      "api://<mcp-api-app-id>"
    ],
    "ScopePrefix": "api://<mcp-api-app-id>/"
  }
}

Why each value matters

  • identity-provider-discovery-endpoint enables OAuth mode at startup
  • ResourceUrl must match the exact canonical client-facing URL
  • Audiences should include both GUID and api:// forms
  • ScopePrefix ensures clients request Entra-qualified MCP scopes

Step 4 - Connect the Web Client AI Assistant (Optional)

The Web Client can consume the same MCP endpoint server-to-server through its own app registration <webclient-app-id>.

Because this flow is non-interactive, grant consent in advance:

  1. Open the Web Client app registration in Entra ID.
  2. Add delegated permissions for the MCP API (mcp:* scopes).
  3. Grant admin consent for the tenant.

If this consent is missing, the assistant may show no tools and diagnostics can include AADSTS65001.

Configure Web Client appsettings.json:

"Services": {
  "nodinite-mcpserver": {
    "http": {
      "0": "https://mcp.example.com:44005"
    }
  }
},
"Mcp": {
  "McpServerScope": "api://<mcp-api-app-id>/.default"
}

Use the canonical base URL (without /mcp) in Services.

Step 5 - Connect from Visual Studio Code

Add the server in user or workspace MCP configuration:

{
  "servers": {
    "nodinite": {
      "type": "http",
      "url": "https://mcp.example.com:44005/mcp"
    }
  }
}

Start the server from MCP tools in Visual Studio Code. The client discovers OAuth metadata automatically, opens sign-in, and then loads Nodinite tools.

Quick Validation Prompt

Use a direct verification prompt:

  • List my Nodinite monitor views.

Verifying a Deployment

From a client machine:

curl https://mcp.example.com:44005/.well-known/oauth-protected-resource

Expected response should include:

  • resource with the exact canonical endpoint URL
  • authorization_servers pointing to your Entra tenant
  • scopes_supported with api://<mcp-api-app-id>/... prefixes

Troubleshooting

Symptom Most likely cause Recommended fix
AADSTS65001 and assistant shows no tools Web Client app consent missing Add delegated mcp:* API permissions and grant admin consent
Sign-in works, tools return 401 Token aud does not match configured audiences Include both audience forms in Authentication:Audiences
VS Code loops sign-in or refuses server resource mismatch against client URL Align Mcp:ResourceUrl with canonical URL and recycle
Scope-related Entra error mentions Graph ScopePrefix missing or empty Set ScopePrefix to api://<mcp-api-app-id>/
IIS returns 500.30 on startup Invalid startup config or malformed JSON Validate appsettings.json and inspect application event log
Immediate connection reset URL scheme/host does not match IIS binding Use canonical URL and verify binding configuration
Client timeout Firewall or network path blocks MCP port Validate port path across server, cloud, and client egress
DNS resolves incorrectly on some machines Hosts file or local DNS override Correct local override and re-test
Works in one MCP client but not another Pre-authorization is per client ID Add that client ID or grant consent specifically

Security Recommendations

  • Always use HTTPS with trusted certificates because clients send Bearer tokens on each call.
  • Restrict inbound source IP ranges where operationally possible.
  • Keep OAuth scopes least-privilege and map access to required tool groups.
  • Treat LLM-provider keys as secrets and rotate if they appear in logs or chat text.

Next Step