Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,14 @@ project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

### Added

- **Bounded install-source attribution.** The `start` command accepts optional
`--install-source`, `--install-content`, and `--install-campaign` arguments (plus
environment-variable equivalents) and appends their validated, non-personal labels to
the existing Graph/ARM request `User-Agent`. After MCP initialization, the server also
maps the self-reported client name to a bounded agent-host label (for example `vscode`
or `claude-code`); unknown raw client names are never transmitted.
`--no-install-attribution` provides an explicit opt-out for all attribution labels. The
README install links declare `github-readme` as their source.
- **Per-instance data directory.** New `--data-dir <path>` flag and `SPE_DATA_DIR`
environment variable select where the provisioning `state.json` and MSAL token
cache are stored (precedence: flag > env > default `~/.spe-mcp`). Point each
Expand Down
21 changes: 11 additions & 10 deletions NOTICE.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,22 +18,23 @@ help documentation and our privacy statement. Your use of the software operates
consent to these practices.

> **What this build sends.** `@microsoft/spe-mcp` opens **no separate telemetry channel** and
> sends **no usage analytics or personal, tenant, or per-user data** to Microsoft. The only
> Microsoft-bound signal is a static product `User-Agent` token
> (`spe-mcp-server/<version>`) attached to the Microsoft Graph and Azure Resource Manager
> requests you already make on your own behalf; it carries no personal, tenant, or usage
> data and is used only for aggregate traffic attribution. It is **on by default** and can be
> sends **no usage analytics or personal, tenant, or per-user data** to Microsoft. Its only
> Microsoft-bound signals are a product `User-Agent` token (`spe-mcp-server/<version>`) and
> optional bounded install-source, content, campaign, and self-reported agent-host tokens
> attached to the Microsoft Graph and Azure Resource Manager requests you already make on your
> own behalf. They carry no personal, tenant, or usage data and are used only for aggregate
> traffic attribution. Attribution is **on by default** and can be
> suppressed with `SPE_MCP_COLLECT_TELEMETRY=false` (see below). See [PRIVACY.md](PRIVACY.md) and
> [docs/DATA-FLOW.md](docs/DATA-FLOW.md) for the full data-flow description.

## Telemetry configuration

Telemetry collection is controlled by the `SPE_MCP_COLLECT_TELEMETRY` environment variable and is
**on by default**. The only telemetry this build emits is the static product `User-Agent`
token (`spe-mcp-server/<version>`) stamped on outbound Graph/ARM requests for aggregate traffic
attribution — there is no usage-analytics channel and no personal, tenant, or per-user data. To
opt out, set `SPE_MCP_COLLECT_TELEMETRY=false` in your environment; the product token is then
omitted from all outbound requests.
**on by default**. The only telemetry this build emits is the product and optional bounded
attribution tokens in the `User-Agent` stamped on outbound Graph/ARM requests for aggregate
traffic attribution — there is no usage-analytics channel and no personal, tenant, or per-user
data. To opt out, set `SPE_MCP_COLLECT_TELEMETRY=false` in your environment; all attribution
tokens are then omitted from outbound requests.

## Compliance responsibility

Expand Down
34 changes: 21 additions & 13 deletions PRIVACY.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ organization's agreements with Microsoft.
## What the tool collects and sends

**The tool opens no dedicated usage-analytics channel and sends no personal, tenant, or
per-user data to Microsoft.** The only Microsoft-bound attribution signal is a static product
`User-Agent` token, which is on by default and can be turned off (see
per-user data to Microsoft.** Its Microsoft-bound attribution signals are bounded `User-Agent`
tokens, which are on by default and can be turned off (see
[Turning it off](#turning-it-off)). Specifically:

- **No telemetry channel.** The tool does not implement application telemetry and does not
Expand All @@ -26,12 +26,16 @@ per-user data to Microsoft.** The only Microsoft-bound attribution signal is a s
endpoints — Microsoft Graph and Azure Resource Manager — **on your behalf**, in **your**
tenant and subscription. The content and directory data involved flow between your machine
and those Microsoft services; the tool adds no additional recipients.
- **Product `User-Agent`.** Outbound Graph/ARM requests are stamped with a static
`User-Agent` of the form `spe-mcp-server/<version>` (`src/user-agent.ts`). It contains
**no personal, tenant, or usage information** and exists only so the service can measure
aggregate traffic driven by this tool. It is a request header on calls you already make —
not a separate data feed — and it is **on by default**; set `SPE_MCP_COLLECT_TELEMETRY=false`
to omit it (see [Turning it off](#turning-it-off)).
- **Product and install-source `User-Agent`.** Outbound Graph/ARM requests are stamped
with `spe-mcp-server/<version>` (`src/user-agent.ts`). Install links can also configure
bounded source, content, and campaign labels such as `microsoft-learn` and an article
slug. The MCP handshake's self-reported client name is mapped to a bounded agent-host
label; the raw name and client version are not transmitted in the request metadata.
These labels contain **no personal or tenant identifiers**, but they accompany each
authenticated request and Microsoft services can associate them with that request in
normal service logs. They exist so the service can measure aggregate traffic driven by
published install surfaces and agent hosts; they are not a separate data feed. Attribution
is **on by default**; set `SPE_MCP_COLLECT_TELEMETRY=false` to omit all of these tokens.

See [docs/DATA-FLOW.md](docs/DATA-FLOW.md) for the full list of network endpoints and what
travels to each.
Expand All @@ -40,7 +44,7 @@ travels to each.
> software "may collect information about you and your use of the software and send it to
> Microsoft" (full text in [NOTICE.md](NOTICE.md#data-collection)). It is reproduced for
> completeness; **this build opens no usage-analytics channel** — the only Microsoft-bound
> signal is the product `User-Agent` attribution token described above, which is on by default
> signals are the bounded `User-Agent` attribution tokens described above, which are on by default
> and can be turned off (see [Turning it off](#turning-it-off) and the
> [Telemetry configuration](NOTICE.md#telemetry-configuration) note).

Expand All @@ -62,10 +66,14 @@ terms, which are outside the control of this project.

## Turning it off

The product `User-Agent` attribution token (`spe-mcp-server/<version>`) is the only
Microsoft-bound telemetry signal, and it is **on by default**. To opt out, set
`SPE_MCP_COLLECT_TELEMETRY=false` in your environment; the tool then omits the token from all
outbound Graph and Azure Resource Manager requests. Those requests still go out — they simply
Because the tool has no telemetry channel, there is no separate telemetry stream to opt out
of. To omit install-source labels while retaining the product token, remove the
`--install-source`, `--install-content`, and `--install-campaign` arguments from the MCP
client configuration. To omit both install-source and agent-host labels, add
`--no-install-attribution`. All attribution is **on by default**. To opt out, set
`SPE_MCP_COLLECT_TELEMETRY=false` in your environment; the tool then omits the product,
install-source, content, campaign, and agent-host tokens from all outbound Graph and Azure
Resource Manager requests. Those requests still go out — they simply
carry the underlying tool's default `User-Agent` instead (e.g. the Azure CLI's own token for
`az`/`azd`, or the Node runtime default for direct Graph calls), whose logging is governed by
those services' own terms. To further limit
Expand Down
112 changes: 91 additions & 21 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,24 @@ The server exposes **40 tools**, plus an MCP **Prompt** (`provision_spe_app`) an
Run the published npm package directly from your MCP client with `npx`; no
global install is required.

### One-click install

[Install in Visual Studio Code](https://aka.ms/spe-mcp/install/github/vscode)

One-click install is also available for [Visual Studio Code Insiders](https://aka.ms/spe-mcp/install/github/vscode-insiders), [Visual Studio](https://aka.ms/spe-mcp/install/github/visual-studio), and [Cursor](https://aka.ms/spe-mcp/install/github/cursor). From the command line, run `claude mcp add spe -- npx -y @microsoft/spe-mcp start --install-source github-readme --install-content readme-install --install-campaign docs-install-buttons` for Claude Code or `codex mcp add spe -- npx -y @microsoft/spe-mcp start --install-source github-readme --install-content readme-install --install-campaign docs-install-buttons` for the Codex CLI.

These configurations add bounded, non-personal install-source labels to the
existing Graph and Azure request `User-Agent`; they create no separate telemetry
channel. Remove the three install-attribution arguments, or add
`--no-install-attribution`, to omit the labels.

After the MCP handshake, the server also maps the client's self-reported
`clientInfo.name` to a bounded agent-host value such as `vscode`, `cursor`, or
`claude-code`. Unrecognized names become `other`; missing or generic SDK values
become `unknown`. The raw client name and client version are not transmitted, and
the classification is used only for attribution—not for authorization or any
security decision.

### VS Code / Cursor

Add an MCP server entry to `.vscode/mcp.json` (VS Code) or your Cursor MCP
Expand All @@ -88,7 +106,17 @@ configuration:
"spe": {
"type": "stdio",
"command": "npx",
"args": ["-y", "@microsoft/spe-mcp"]
"args": [
"-y",
"@microsoft/spe-mcp",
"start",
"--install-source",
"github-readme",
"--install-content",
"readme-install",
"--install-campaign",
"docs-install-buttons"
]
}
}
}
Expand All @@ -106,7 +134,17 @@ Add to `%APPDATA%\Claude\claude_desktop_config.json` (Windows) or
"mcpServers": {
"spe": {
"command": "npx",
"args": ["-y", "@microsoft/spe-mcp"]
"args": [
"-y",
"@microsoft/spe-mcp",
"start",
"--install-source",
"github-readme",
"--install-content",
"readme-install",
"--install-campaign",
"docs-install-buttons"
]
}
}
}
Expand Down Expand Up @@ -197,8 +235,12 @@ The server accepts configuration via CLI flags or environment variables:
| `--tenant-id` | `SPE_TENANT_ID` | Entra ID Tenant ID |
| `--read-only` | `SPE_READ_ONLY` | Advertise/allow only read/list/get/search tools; reject mutating calls |
| `--tools` | `SPE_TOOLS` | Restrict exposed tools to a profile (`readOnly`, `docsOnly`, `provisioning`, `content`, `admin`) or a comma-separated tool list |
| `--install-source` | `SPE_INSTALL_SOURCE` | Optional bounded install surface: `microsoft-learn`, `github-readme`, `github-release`, `mcp-registry`, `npm`, or `other` |
| `--install-content` | `SPE_INSTALL_CONTENT` | Optional bounded content identifier: `readme-install`, `sharepoint-embedded-mcp-server`, `quickstart-vscode`, `create-container-type`, or `create-manage-containers`; requires an install source |
| `--install-campaign` | `SPE_INSTALL_CAMPAIGN` | Optional bounded campaign identifier: `docs-install-buttons`; requires an install source |
| `--no-install-attribution` | `SPE_INSTALL_ATTRIBUTION=off` | Omit install-source and agent-host labels from outbound request metadata |
| `--data-dir` | `SPE_DATA_DIR` | Directory for the token cache + provisioning state (default `~/.spe-mcp`). Point each instance at a unique **absolute** path (or `~/...`; CWD-relative paths are rejected) to run multiple servers without clobbering state |
| _(none)_ | `SPE_MCP_COLLECT_TELEMETRY` | Product `User-Agent` attribution token on outbound Graph/ARM requests. On by default; set to `false` to opt out (see [PRIVACY.md](PRIVACY.md)) |
| _(none)_ | `SPE_MCP_COLLECT_TELEMETRY` | Product and optional bounded `User-Agent` attribution tokens on outbound Graph/ARM requests. On by default; set to `false` to opt out (see [PRIVACY.md](PRIVACY.md)) |

> The CLI flag wins when both a flag and its env var are set. Run
> `spe-mcp start --help` to see the authoritative option list and descriptions.
Expand Down Expand Up @@ -278,7 +320,7 @@ Add to `%APPDATA%\Claude\claude_desktop_config.json` (Windows) or `~/Library/App

```bash
# Start the MCP server (stdio transport)
spe-mcp start [--client-id ID] [--tenant-id ID] [--read-only] [--tools <profileOrCsv>]
spe-mcp start [--client-id ID] [--tenant-id ID] [--read-only] [--tools <profileOrCsv>] [--install-source <source>]

# Authenticate interactively (cache tokens for headless use)
spe-mcp auth --client-id ID --tenant-id ID [--reset]
Expand All @@ -296,6 +338,10 @@ Every command has built-in help — run `spe-mcp <command> --help` (e.g.
| `--tenant-id <id>` | Entra ID Tenant ID. Discovered from the Azure CLI when omitted. |
| `--read-only` | Read-only mode: only read/list/get/search tools are exposed and callable. |
| `--tools <profileOrCsv>` | Tool allowlist: a profile (`readOnly`, `docsOnly`, `provisioning`, `content`, `admin`) or a comma-separated list of tool names. |
| `--install-source <source>` | Add a bounded install surface to the existing Graph/ARM request `User-Agent`. |
| `--install-content <id>` | Add one of the bounded content identifiers listed in [Configuration](#configuration); requires `--install-source`. |
| `--install-campaign <id>` | Add the bounded `docs-install-buttons` campaign identifier; requires `--install-source`. |
| `--no-install-attribution` | Omit install-source and agent-host labels from outbound request metadata. |

## Authentication

Expand Down Expand Up @@ -342,12 +388,32 @@ The data directory holds a single provisioning `state.json` plus the token cache
"servers": {
"spe-tenantA": {
"command": "npx",
"args": ["-y", "@microsoft/spe-mcp", "start"],
"args": [
"-y",
"@microsoft/spe-mcp",
"start",
"--install-source",
"github-readme",
"--install-content",
"readme-install",
"--install-campaign",
"docs-install-buttons"
],
"env": { "SPE_DATA_DIR": "~/.spe-mcp-tenantA", "SPE_TENANT_ID": "<tenant-A>" }
},
"spe-tenantB": {
"command": "npx",
"args": ["-y", "@microsoft/spe-mcp", "start"],
"args": [
"-y",
"@microsoft/spe-mcp",
"start",
"--install-source",
"github-readme",
"--install-content",
"readme-install",
"--install-campaign",
"docs-install-buttons"
],
"env": { "SPE_DATA_DIR": "~/.spe-mcp-tenantB", "SPE_TENANT_ID": "<tenant-B>" }
}
}
Expand Down Expand Up @@ -388,7 +454,7 @@ src/
├── resources.ts — MCP Resources (reference architectures)
├── reference-architectures.ts — Reference-architecture catalog (reads ../samples/)
├── elicitation.ts — Interactive consent / step-up prompts
├── user-agent.ts — Product User-Agent token + SPE_MCP_COLLECT_TELEMETRY opt-out
├── user-agent.ts — Product/bounded User-Agent attribution + telemetry opt-out
├── types.ts — Shared TypeScript types
└── tools/ — 31 tools across 28 modules (one McpTool per export)
├── status.ts — status_get
Expand Down Expand Up @@ -592,29 +658,33 @@ Resource Manager — **on your behalf**; the content and directory data involved
between your machine, your MCP client, and those Microsoft services in your own
tenant/subscription.

The server opens **no separate telemetry channel** and sends **no usage analytics** to
Microsoft. Outbound Graph/ARM requests carry a **static product `User-Agent`**
(`spe-mcp-server/<version>`) that contains **no personal, tenant, or usage data** and is
used only for aggregate traffic attribution. That attribution token is **on by default** and
can be suppressed with `SPE_MCP_COLLECT_TELEMETRY=false` (see **Telemetry configuration** below).
Authentication tokens are cached locally with owner-only permissions (**SEC-003**). For
details see [PRIVACY.md](PRIVACY.md) and [docs/DATA-FLOW.md](docs/DATA-FLOW.md); Microsoft's
handling of data you send to its online services is described in the
The server opens **no separate telemetry channel**. Each authenticated Graph/ARM request
carries a product `User-Agent` (`spe-mcp-server/<version>`). An install configuration can
add bounded source, content, campaign, and self-reported agent-host labels to that
request header. The raw MCP client name and version are not sent in these labels.
The labels contain no personal or tenant identifiers, but Microsoft services can
associate them with the authenticated request in normal service logs. Omit install and
agent-host labels with `--no-install-attribution`, or all attribution tokens with
`SPE_MCP_COLLECT_TELEMETRY=false`. Authentication tokens are cached locally with owner-only
permissions (**SEC-003**). For details see [PRIVACY.md](PRIVACY.md) and
[docs/DATA-FLOW.md](docs/DATA-FLOW.md); Microsoft's handling of data you send to its online
services is described in the
[Microsoft Privacy Statement](https://privacy.microsoft.com/privacystatement).

**Data collection (standard Microsoft notice).** The software may collect information about
you and your use of the software and send it to Microsoft; Microsoft may use this information
to provide and improve products and services, and your use of the software operates as your
consent to these practices (full text in [NOTICE.md](NOTICE.md#data-collection)). **This
build opens no usage-analytics channel** — the only Microsoft-bound signal is the product
`User-Agent` attribution token described above, which you can turn off with
build opens no usage-analytics channel** — its only Microsoft-bound signals are the bounded
`User-Agent` attribution tokens described above, which you can turn off with
`SPE_MCP_COLLECT_TELEMETRY=false`.

**Telemetry configuration.** Attribution is gated by the `SPE_MCP_COLLECT_TELEMETRY` environment
variable and is **on by default**. The only telemetry emitted is the static product
`User-Agent` token on outbound Graph/ARM requests (aggregate traffic attribution — no usage
analytics, no personal/tenant/per-user data). Set `SPE_MCP_COLLECT_TELEMETRY=false` to omit the
token from all outbound requests; those requests then fall back to the underlying tool's
variable and is **on by default**. The only telemetry emitted is the product and optional
bounded attribution tokens in the `User-Agent` on outbound Graph/ARM requests (aggregate
traffic attribution — no usage analytics or personal/tenant/per-user data). Set
`SPE_MCP_COLLECT_TELEMETRY=false` to omit all attribution tokens from outbound requests;
those requests then fall back to the underlying tool's
default `User-Agent` (the Azure CLI's own token for `az`/`azd`; the Node runtime default for
direct Graph calls).

Expand Down
Loading
Loading