A read-only MCP server for querying Microsoft Dataverse environments during development
Project description
Dataverse MCP Server
An MCP server for interacting with Microsoft Dataverse environments. Built with FastMCP and the official PowerPlatform-Dataverse-Client Python SDK.
Features
- Solution inspection — list solutions, get solution details, browse solution components
- Table querying — flexible OData-style queries against any Dataverse table
- Schema exploration — list tables, inspect table metadata (primary key, name attribute)
- Agent-friendly — rich tool descriptions designed for AI agent discoverability
- Secure — Pydantic v2 input validation, GUID format enforcement, OData injection prevention
Prerequisites
- uv — install from docs.astral.sh/uv
- Access to a Microsoft Dataverse environment
- Azure CLI (
az login) or a registered app for authentication
Installation
No install required — run directly from PyPI using uvx:
uvx dataverse-mcp
uvx downloads and runs the package in an isolated environment. No cloning, no virtual env setup.
Configuration
Copy the example environment file and fill in your values:
cp .env.example .env
| Variable | Required | Default | Description |
|---|---|---|---|
DATAVERSE_URL |
Yes | — | Your Dataverse org URL (e.g., https://yourorg.crm.dynamics.com) |
DATAVERSE_AUTH_TYPE |
No | azure_cli |
Auth method: interactive, client_secret, or azure_cli |
AZURE_TENANT_ID |
For client_secret |
— | Azure AD tenant ID |
AZURE_CLIENT_ID |
For client_secret |
— | App registration client ID |
AZURE_CLIENT_SECRET |
For client_secret |
— | App registration client secret |
Authentication Methods
azure_cli(default) — Uses your existingaz loginsession. Best for local development.interactive— Opens a browser window for interactive sign-in.client_secret— Uses a service principal. RequiresAZURE_TENANT_ID,AZURE_CLIENT_ID, andAZURE_CLIENT_SECRET.
Usage
This server communicates over stdio and works with any MCP-compatible client.
VS Code
Add the server to your VS Code MCP configuration (.vscode/mcp.json):
{
"servers": {
"dataverse-mcp": {
"type": "stdio",
"command": "uvx",
"args": ["dataverse-mcp"],
"env": {
"DATAVERSE_URL": "https://yourorg.crm.dynamics.com",
"DATAVERSE_AUTH_TYPE": "azure_cli"
}
}
}
}
To connect to multiple environments, add one entry per environment with a unique key:
{
"servers": {
"dataverse-mcp-dev": {
"type": "stdio",
"command": "uvx",
"args": ["dataverse-mcp"],
"env": {
"DATAVERSE_URL": "https://yourorg-dev.crm.dynamics.com",
"DATAVERSE_AUTH_TYPE": "azure_cli"
}
},
"dataverse-mcp-test": {
"type": "stdio",
"command": "uvx",
"args": ["dataverse-mcp"],
"env": {
"DATAVERSE_URL": "https://yourorg-test.crm.dynamics.com",
"DATAVERSE_AUTH_TYPE": "azure_cli"
}
}
}
}
Tools
| Tool | Description |
|---|---|
dataverse_list_solutions |
List solutions with optional OData filter, select, and top |
dataverse_get_solution |
Get a single solution by unique name or GUID |
dataverse_list_solution_components |
List components in a solution with optional type filter |
dataverse_query_table |
Query records from any table with filter, select, orderby, expand, top |
dataverse_get_record |
Get a single record by table name and GUID |
dataverse_list_tables |
List available tables/entities with optional filter |
dataverse_get_table_metadata |
Get schema details for a specific table |
Project Structure
src/dataverse_mcp/
├── __init__.py # Package init
├── _app.py # FastMCP instance (avoids circular imports)
├── server.py # Entry point, logging setup, tool registration
├── client.py # DataverseClient wrapper (auth, lifecycle)
├── models.py # Pydantic v2 input models for all tools
└── tools/
├── __init__.py # Tools package init
├── solutions.py # Solution query tools
├── tables.py # Table record query tools
└── metadata.py # Table/column metadata tools
Development
# Clone the repo
git clone https://github.com/ryanmichaeljames/dataverse-mcp.git
cd dataverse-mcp
# Install dependencies
uv sync
# Run the MCP inspector for testing
uv run mcp dev src/dataverse_mcp/server.py
# Compile check all modules
uv run python -m py_compile src/dataverse_mcp/server.py
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file dataverse_mcp-0.1.0.tar.gz.
File metadata
- Download URL: dataverse_mcp-0.1.0.tar.gz
- Upload date:
- Size: 12.9 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
07b08013c3e5f52e2a1f34cd8b5be4d2fa845f4d58234e341b0007e237e2489a
|
|
| MD5 |
cbfa494952d55ca17db57ce3536fac78
|
|
| BLAKE2b-256 |
4674745947641e33daf60c898980a0feedca41e31229413115906759d1f9f2a8
|
Provenance
The following attestation bundles were made for dataverse_mcp-0.1.0.tar.gz:
Publisher:
release.yml on ryanmichaeljames/dataverse-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
dataverse_mcp-0.1.0.tar.gz -
Subject digest:
07b08013c3e5f52e2a1f34cd8b5be4d2fa845f4d58234e341b0007e237e2489a - Sigstore transparency entry: 1260532379
- Sigstore integration time:
-
Permalink:
ryanmichaeljames/dataverse-mcp@6ac469fda18279c7ba005a3cfbe8e0d57e30ae36 -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/ryanmichaeljames
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@6ac469fda18279c7ba005a3cfbe8e0d57e30ae36 -
Trigger Event:
push
-
Statement type:
File details
Details for the file dataverse_mcp-0.1.0-py3-none-any.whl.
File metadata
- Download URL: dataverse_mcp-0.1.0-py3-none-any.whl
- Upload date:
- Size: 14.8 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c6899c1de6d3b5fbbc6c095797fcf5053ce331ec13638312454caafb9f5694a5
|
|
| MD5 |
bb44d14f3bb997f834bb2f16a177543a
|
|
| BLAKE2b-256 |
0e8675ff8c0b54a946b13627469e267a85403b95db4b670b72d0cf58c6b495f0
|
Provenance
The following attestation bundles were made for dataverse_mcp-0.1.0-py3-none-any.whl:
Publisher:
release.yml on ryanmichaeljames/dataverse-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
dataverse_mcp-0.1.0-py3-none-any.whl -
Subject digest:
c6899c1de6d3b5fbbc6c095797fcf5053ce331ec13638312454caafb9f5694a5 - Sigstore transparency entry: 1260532408
- Sigstore integration time:
-
Permalink:
ryanmichaeljames/dataverse-mcp@6ac469fda18279c7ba005a3cfbe8e0d57e30ae36 -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/ryanmichaeljames
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@6ac469fda18279c7ba005a3cfbe8e0d57e30ae36 -
Trigger Event:
push
-
Statement type: