Skip to main content

Within SDK (Python)

Instrument Model Context Protocol (MCP) servers with privacy-conscious workflow analytics. Within captures MCP activity, builds a catalog of available tools, groups pseudonymous user journeys, creates SDK leads, and connects CRM outcomes back to the workflows that produced them.

Documentation · Quickstart · API Reference · Get an API key

Installation

pip install within-sdk

The SDK requires Python 3.11 or later and supports official MCP servers (mcp 1.2+ and 2.x — both FastMCP and MCPServer), community FastMCP v2 servers (pip install "within-sdk[community]"), and low-level mcp servers.

Environment

Configure the vendor slug created during onboarding and its SDK API key in the server process that runs your MCP server:

WITHIN_VENDOR_SLUG=acme
WITHIN_SDK_API_KEY=within_sk_xxx

Keep the API key in server-side environment or secret storage. Do not expose it in client code or commit it to source control.

Quickstart

Register your MCP tools first, then call track() on the server instance used by the running process.

import os

from mcp.server import MCPServer  # mcp 1.x: from mcp.server.fastmcp import FastMCP
from within_sdk import track, WithinOptions, UserIdentity

server = MCPServer("acme-mcp")


@server.tool()
def search_companies(query: str) -> str:
    return do_search(query)


def identify(request, context):
    user = lookup_user_from_request(context)  # e.g. claims off context.request
    if not user:
        return None
    return UserIdentity(
        user_id=user.internal_customer_id,
        user_data={"plan": user.plan, "segment": user.segment},
    )


track(server, os.environ["WITHIN_VENDOR_SLUG"], WithinOptions(
    # api_key falls back to WITHIN_SDK_API_KEY — no need to pass it here
    identify=identify,
))

Use a stable, opaque vendor-local ID for user_id rather than an email address, name, or organization domain. The SDK hashes it locally with the vendor slug (SHA-256, byte-identical to the TypeScript SDK and the outcomes connector) before SDK activity leaves your process.

By default, track() instruments MCP initialization, tools/list, and tools/call activity. It also enables tool-call context capture and registers the get_more_tools feedback tool. This changes the advertised tool list and input schemas, while preserving vendor handler arguments and tool results.

Public APIs

track()

track(server, vendor_slug, options=None) -> server

Instruments an official MCPServer/FastMCP, community FastMCP, or compatible low-level MCP server and returns the same server instance. Call it once for each server instance after registering tools. track() never raises into the host server — configuration problems disable analytics and log a warning.

publish_custom_event()

Publish a vendor-defined workflow event associated with a tracked server:

from within_sdk import publish_custom_event, CustomEventData

publish_custom_event(server, "acme", CustomEventData(
    session_id=mcp_session_id,
    user_id=user.internal_customer_id,
    resource_name="checkout_started",
    parameters={"plan": "pro"},
    message="User started checkout after an MCP workflow",
    tags={"channel": "mcp"},
))

When passed a tracked server, the function reuses its SDK API key and Within API origin. Pass session_id to correlate with an MCP journey and user_id when identity is known. Without either, the event starts a fresh anonymous journey. You can also pass an MCP session ID string as the first argument from a process that never called track() — provide api_key in the event data.

report_conversion()

Report a confirmed subscription conversion from trusted server-side checkout, webhook, or account-upgrade code:

from within_sdk import report_conversion

result = report_conversion(
    os.environ["WITHIN_VENDOR_SLUG"],
    os.environ["WITHIN_SDK_API_KEY"],
    user.internal_customer_id,
    converted_at=datetime.now(timezone.utc),
    plan={"id": "pro", "name": "Pro", "interval": "month"},
    metadata={"source": "checkout_webhook"},
)

Only the user id is required. Use the same opaque vendor-local ID returned by identify(); the SDK creates the subject locally before sending. Repeated reports for the same subject on the same UTC day return inserted: False.

get_subject_for_user_id()

Derive the same vendor-scoped subject used by identification and conversion reporting. The operation is local and deterministic, which makes it useful for tests and local verification.

from within_sdk import get_subject_for_user_id

subject = get_subject_for_user_id("acme", user.internal_customer_id)

Configuration

track(server, vendor_slug, options) accepts these commonly used options on WithinOptions:

Option Purpose
api_key Within SDK API key. Falls back to WITHIN_SDK_API_KEY, then WITHIN_SDK_INGEST_KEY.
api_base_url Override the Within API origin. The SDK appends /v1/ingest/*; most integrations should use the default.
identify Resolve a stable vendor-local user_id and optional redacted traits for the current request.
log Replace the default local SDK log destination with a callback.
enable_tracing Capture supported MCP activity. Defaults to True.
enable_tool_call_context Add and capture the tool-call context parameter. Defaults to True.
custom_context_description Replace the default description shown for the injected context parameter.
enable_report_missing Register the get_more_tools feedback tool. Defaults to True.
event_tags Add validated string tags to captured activity.
event_properties Add custom properties to captured activity.
redact_sensitive_information Apply an additional vendor-provided redaction function.
privacy PrivacyOptions — configure field/event byte limits and additional keys to redact.

api_base_url is an origin such as https://api.getwith.in. It falls back to WITHIN_SDK_API_URL, then WITHIN_SDK_INGEST_BASE_URL, and finally https://api.getwith.in. See the API Reference for the complete option and result types.

Privacy and redaction

  • user_id values supplied to identification, custom events, and conversions are hashed locally into subjects.
  • Raw user_id and user_name values are not sent to Within.
  • Identity-like fields in user data, parameters, responses, tags, properties, and conversion metadata are removed or redacted before sending.
  • Configurable field and event limits truncate oversized payloads.
  • The Within API applies an additional server-side Presidio redaction pass for recognized values such as emails, phone numbers, SSNs, card-like values, URLs, IPs, bearer tokens, API keys, and secrets.

Pattern-based redaction cannot guarantee detection of every possible name, location, or sensitive value. Send only data needed for workflow analytics and use opaque identifiers whenever possible.

Documentation

The Within dashboard presents this data as SDK Activity, SDK Leads, Session Replay, Agent Journey Map, Context Explorer, and Missing Tool Demand.

Onboarding: Sign up and get an API key

  1. Create a Within dashboard account using your work email.
  2. Enter the verification code sent to your email, then sign in to the Within dashboard and create a vendor.
  3. Open Settings → SDK Setup, select the vendor, and generate its SDK API key.
  4. Copy the newly displayed key and store it securely. The dashboard does not retain the plaintext key for later display.
  5. Set the key as WITHIN_SDK_API_KEY, set your registered slug as WITHIN_VENDOR_SLUG, and use both values in track().

Forked from mcpcat-python-sdk (MIT).

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

within_sdk-0.1.3.tar.gz (77.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

within_sdk-0.1.3-py3-none-any.whl (86.8 kB view details)

Uploaded Python 3

File details

Details for the file within_sdk-0.1.3.tar.gz.

File metadata

  • Download URL: within_sdk-0.1.3.tar.gz
  • Upload date:
  • Size: 77.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/7.0.0 CPython/3.13.4

File hashes

Hashes for within_sdk-0.1.3.tar.gz
Algorithm Hash digest
SHA256 d5480a22e440fd40d88a54c62143cfe11cdafd982618eebfc438f117bd3f952e
MD5 5de8cae71a3a7f5785cfd2b77d88a461
BLAKE2b-256 1660e682a78ccea842e791fb220bfc99a203b2e2c205df41161585169ddaa795

See more details on using hashes here.

File details

Details for the file within_sdk-0.1.3-py3-none-any.whl.

File metadata

  • Download URL: within_sdk-0.1.3-py3-none-any.whl
  • Upload date:
  • Size: 86.8 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/7.0.0 CPython/3.13.4

File hashes

Hashes for within_sdk-0.1.3-py3-none-any.whl
Algorithm Hash digest
SHA256 f829d81aec64587ee79bad87b0c4147585148021aaa5aaa9e65b8fbd1ab19f39
MD5 0525b3acb73e3fc3d955e096e53c5d8c
BLAKE2b-256 5b59f5134fa0944cf1060047f8fe4fea20087182f4eb7d9c0309b854fb325518

See more details on using hashes here.

Release history Release notifications | RSS feed

0.1.5

2 files

0.1.4

2 files

This release

0.1.3 This release

2 files

0.1.2

2 files

0.1.1

2 files

0.1.0

2 files

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