Skip to main content

Salesforce MCP Server

A custom-built, self-hosted MCP server that lets AI agents (Claude Desktop, Claude Code, the MCP Inspector, or any other MCP client) connect to Salesforce — to query, search, and modify data in an org.

Not a Salesforce product. This is an independent, personal learning project — not affiliated with, endorsed by, or supported by Salesforce, Inc. Full explanation: docs/ARCHITECTURE.md.

New to MCP? If "server," "client," and "tool call" aren't already familiar terms, read docs/MCP_PRIMER.md first — five minutes, and everything else here will make more sense.

Quickstart

You'll need: a Salesforce org with an External Client App set up — a free Developer Edition org works fine — and its Consumer Key in hand. docs/SETUP.md walks through creating that (10–15 min); do it first, then come back here.

Three ways to get a running server — pick whichever fits:

Option A — uvx (fastest; no clone, no venv; requires uv):

export SF_LOGIN_URL=https://your-domain.my.salesforce.com
export SF_CLIENT_ID=your-client-id
uvx --from sf-mcp-server sf-mcp-login   # one-time interactive login — opens your browser
uvx sf-mcp-server

(sf-mcp-login needs the explicit --from sf-mcp-server — uv only infers the package name from a bare command when they match, and this package provides two commands. sf-mcp-server matches its own package name, so it doesn't need --from.)

Or drop straight into an MCP client's config (Claude Desktop's claude_desktop_config.json, Claude Code's .mcp.json) with "command": "uvx", "args": ["sf-mcp-server"] and the same env vars, plus SF_PKCE_TOKEN_CACHE set to an absolute path (the client launches the server from its own working directory, not wherever you ran sf-mcp-login, so the default relative cache path won't be found otherwise) — see docs/USAGE.md for the full config example. That login step is only needed once — see docs/AUTHENTICATION.md for what it does and why, and for the alternative Client Credentials Flow (SF_CLIENT_SECRET, no login step) if you'd rather use a fixed service identity instead.

Option B — Python from source (for contributing, or if you'd rather not use uv):

git clone <this-repo-url> && cd salesforce-mcp-server
python3 -m venv .venv && source .venv/bin/activate
pip install -e ".[dev]"
cp .env.example .env   # fill in SF_LOGIN_URL / SF_CLIENT_ID
python -m salesforce_mcp.login   # one-time interactive login — opens your browser
python -m salesforce_mcp.server

Option C — Docker (no Python setup needed; requires Docker installed and running — check with docker info):

git clone <this-repo-url> && cd salesforce-mcp-server
docker build -t salesforce-mcp-server .
docker run --rm -i \
  -e SF_LOGIN_URL=https://your-domain.my.salesforce.com \
  -e SF_CLIENT_ID=your-client-id \
  -e SF_CLIENT_SECRET=your-client-secret \
  -e SF_AUTH_FLOW=client_credentials \
  -e MCP_TRANSPORT=stdio \
  salesforce-mcp-server

Docker explicitly pins SF_AUTH_FLOW=client_credentials here rather than using the default interactive login — there's no browser or display inside a container for that flow to use. See docs/AUTHENTICATION.md if you actually want PKCE in a container anyway (mount a pre-existing .salesforce_pkce_token.json from the host).

Whichever you pick, that's it running. Next: point the MCP Inspector or Claude Desktop at it and actually try a tool — see docs/USAGE.md.

Quick note on that -e MCP_TRANSPORT=stdio flag in Option C: Python vs. Docker and stdio vs. HTTP are two separate choices, not tied together — Python defaults to stdio and Docker's image defaults to HTTP purely for convenience, but all four combinations actually work. See docs/MCP_PRIMER.md#the-two-transports-stdio-and-streamable-http for what each transport actually is and why. For hosting this on a network instead of running it locally, see docs/DEPLOYMENT.md.

What it can do

  • Query & search — sf_query (SOQL, auto-paginated), sf_search (SOSL)
  • Record CRUD — sf_get_record, sf_create_record, sf_update_record, sf_upsert_record (by external ID), sf_delete_record
  • Bulk API 2.0 — sf_bulk_query, sf_bulk_load, for record volumes too large for the one-record-per-call REST tools above
  • Composite — sf_composite, to bundle several sub-requests into one atomic call
  • Describe/discovery — sf_describe_object, sf_list_objects (trimmed fields + optional name_contains/custom_only filters, so it doesn't dump 800+ objects' full raw metadata), also available as MCP Resources (salesforce://objects, salesforce://schema/{sobject})
  • Ops — sf_api_usage (quick API-limit check), sf_org_health (fuller report: org info, all limits, and license seat usage)
  • Custom APIs — sf_call_apex_rest calls any custom Apex REST endpoint (@RestResource) your org exposes, no code changes needed — see docs/USAGE.md
  • Prompts — ready-made task templates for common requests: summarize_account, draft_followup_email, data_hygiene_check — see docs/USAGE.md
  • Platform events / Change Data Capture — sf_subscribe_platform_event replays a bounded batch of events from a platform event or CDC channel, honoring Salesforce's 72-hour Pub/Sub API retention window — see docs/USAGE.md
  • Elicitation — confirms before an unscoped sf_query/sf_search or any delete (sf_delete_record, sf_bulk_load(operation="delete")); disable with SF_ELICITATION_ENABLED=false — see docs/USAGE.md
  • Two auth options — the default interactive "Login with Salesforce" (OAuth Authorization Code + PKCE, per-user), via python -m salesforce_mcp.login or the in-session sf_login tool, or the OAuth Client Credentials Flow (one fixed service identity) for headless/shared use, switched with SF_AUTH_FLOW=client_credentials — see docs/AUTHENTICATION.md
  • Resilient by default — retries transient (5xx / REQUEST_LIMIT_EXCEEDED) Salesforce errors automatically; every other error comes back as a clean, readable message instead of a stack trace

Every tool above talks to a standard Salesforce API out of the box — none of them are specific to any one org. Two ways to add your own: call sf_call_apex_rest (works today, zero code) or add a first-class tool of your own — docs/EXTENDING.md is a step-by-step guide.

Running it remotely (cloud)

The same server also runs as a container behind a network-reachable Streamable HTTP endpoint, for when you want an agent that isn't on the same machine to reach it. This has been built and run locally with Docker and confirmed working — it has not yet been deployed to a real cloud account. docs/DEPLOYMENT.md has the full picture, including that caveat up front, plus two ready-to-try recipes (GCP Cloud Run, AWS App Runner).

Tests

pytest tests/ -v      # all Salesforce calls are mocked with respx — no live org needed
ruff check src tests

This is the automated suite — fast, no Salesforce org or Docker required. There are two other, manual checks, each testing something different: Inspector-against-a-real-org (functional — see docs/USAGE.md) and Docker-build-and-curl (plumbing only — see docs/DEPLOYMENT.md).

Documentation

Read in this order if you're getting started:

# Doc For
1 docs/MCP_PRIMER.md New to MCP — what a server/client/tool call actually is
2 docs/SETUP.md Creating the Salesforce org + integration, .env config
3 docs/AUTHENTICATION.md Both auth flows side by side — Client Credentials vs. "Login with Salesforce" (PKCE)
4 docs/USAGE.md Running it — Claude Desktop, Claude Code, MCP Inspector, example prompts
5 docs/DEPLOYMENT.md Hosting it in the cloud instead of locally
6 docs/EXTENDING.md Adding your own tool for a custom API
7 docs/RELEASING.md Maintainers only — how a PyPI release actually gets published
8 docs/ARCHITECTURE.md Optional — how and why it was built this way

License

MIT

Metadata

Release files for sf-mcp-server 0.1.1

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for sf-mcp-server 0.1.1
File Size Uploaded Provenance
sf_mcp_server-0.1.1.tar.gz 91.7 kB With provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for sf-mcp-server 0.1.1
File Interpreter ABI Platform
sf_mcp_server-0.1.1-py3-none-any.whl Python 3 none any Details

Total release size: 144.6 kB

Release files / sf_mcp_server-0.1.1.tar.gz

Download URL sf_mcp_server-0.1.1.tar.gz
Size 91.7 kB
Tags Source
SHA-256 checksum
How to use checksums
f3fad8cb8c935d2f9046bf536a5f0e54912e8c29e4ac6bad30602c00a5610b21
BLAKE2b-256 checksum
How to use checksums
4bff49716c13d6e4b4e36850e62c9553b786b48a9c76c4ad9f27072d04b65d41
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 6, 2026.

Transparency log

Release files / sf_mcp_server-0.1.1-py3-none-any.whl

Download URL sf_mcp_server-0.1.1-py3-none-any.whl
Size 53.0 kB
Tags Python 3
SHA-256 checksum
How to use checksums
522de4e3261348163bfd462d744a1322bfc971829692b7b4430616a98c62e72e
BLAKE2b-256 checksum
How to use checksums
c81751e89e549e0b3272230910523e4b672adf722bce4c60d8a529821aea20a4
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 6, 2026.

Transparency log

Security for sf-mcp-server 0.1.1

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

Full provenance

All 2 files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for sf_mcp_server-0.1.1.tar.gz

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 6, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.1.1 This release

2 release files Full provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page