UNPKG

skills-ws

Version:

87 agent skills for AI coding assistants — marketing, growth, web3, dev, design & operations. Built for OpenClaw, Claude Code, Cursor, and Codex.

122 lines (96 loc) • 5.39 kB
## Contents - 2. Programmatic client (official SDK) - 2.1 Connect to a remote server (Streamable HTTP) — TypeScript - 2.2 Connect to a local server (stdio) — TypeScript - 2.3 Streamable HTTP with SSE fallback (support old + new servers) - 2.4 Python client (Streamable HTTP, with stdio + legacy SSE shown) ## 2. Programmatic client (official SDK) Install: `npm i @modelcontextprotocol/sdk` (TypeScript) or `pip install mcp` / `uv add mcp` (Python). The TypeScript SDK uses subpath imports under `@modelcontextprotocol/sdk/...`. (As of Jun 2026; check the current import paths and package name at https://github.com/modelcontextprotocol/typescript-sdk and https://github.com/modelcontextprotocol/python-sdk before pinning.) ### 2.1 Connect to a remote server (Streamable HTTP) — TypeScript ```typescript import { Client } from '@modelcontextprotocol/sdk/client/index.js'; import { StreamableHTTPClientTransport } from '@modelcontextprotocol/sdk/client/streamableHttp.js'; const client = new Client( { name: 'my-agent', version: '1.0.0' }, // Advertise the client capabilities you actually implement (see §3.4). { capabilities: { /* roots: { listChanged: true }, sampling: {}, elicitation: {} */ } } ); const transport = new StreamableHTTPClientTransport( new URL('https://api.example.com/mcp'), { // Provider-specific static headers (API key, etc.). For OAuth, prefer authProvider — see §5. requestInit: { headers: new Headers({ Authorization: `Bearer ${process.env.MCP_TOKEN}` }), }, } ); await client.connect(transport); // performs the initialize handshake for you // ... use the client (see §3) ... await client.close(); ``` `client.connect()` runs the full `initialize` exchange: it sends the client's protocol version + capabilities + `clientInfo`, receives the server's negotiated version + capabilities + `serverInfo`, and sends the `notifications/initialized` ack. You don't hand-roll JSON-RPC. ### 2.2 Connect to a local server (stdio) — TypeScript ```typescript import { Client } from '@modelcontextprotocol/sdk/client/index.js'; import { StdioClientTransport } from '@modelcontextprotocol/sdk/client/stdio.js'; const transport = new StdioClientTransport({ command: 'npx', args: ['-y', '@scope/some-mcp-server'], env: { ...process.env, SOME_API_KEY: process.env.SOME_API_KEY ?? '' }, // pass only what's needed }); const client = new Client({ name: 'my-agent', version: '1.0.0' }); await client.connect(transport); ``` Secrets reach a local server via its **environment**, not the command line (args are visible in `ps`). Pass an explicit `env` allowlist rather than leaking your whole environment. ### 2.3 Streamable HTTP with SSE fallback (support old + new servers) This is the canonical compatibility pattern from the SDK docs: ```typescript import { Client } from '@modelcontextprotocol/sdk/client/index.js'; import { StreamableHTTPClientTransport } from '@modelcontextprotocol/sdk/client/streamableHttp.js'; import { SSEClientTransport } from '@modelcontextprotocol/sdk/client/sse.js'; async function connectRemote(url: string) { const baseUrl = new URL(url); try { // Preferred: modern Streamable HTTP const client = new Client({ name: 'my-agent', version: '1.0.0' }); const transport = new StreamableHTTPClientTransport(baseUrl); await client.connect(transport); return { client, transport }; } catch { // Legacy fallback: old HTTP+SSE servers (deprecated 2025-03-26) const client = new Client({ name: 'my-agent', version: '1.0.0' }); const transport = new SSEClientTransport(baseUrl); await client.connect(transport); return { client, transport }; } } ``` ### 2.4 Python client (Streamable HTTP, with stdio + legacy SSE shown) ```python import asyncio from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client from mcp.client.streamable_http import streamablehttp_client # preferred for remote # from mcp.client.sse import sse_client # legacy fallback only async def remote(): # Provider-specific auth headers; for OAuth see the SDK auth helpers (§5). headers = {"Authorization": "Bearer <token>"} async with streamablehttp_client( "https://api.example.com/mcp", headers=headers, timeout=30 ) as (read, write, _get_session_id): async with ClientSession(read, write) as session: await session.initialize() tools = await session.list_tools() print("tools:", [t.name for t in tools.tools]) result = await session.call_tool("dns_lookup", {"domain": "example.com"}) print(result.content) async def local(): params = StdioServerParameters(command="uvx", args=["some-mcp-server"], env=None) async with stdio_client(params) as (read, write): async with ClientSession(read, write) as session: await session.initialize() print((await session.list_tools()).tools) asyncio.run(remote()) ``` > SDK note (Jun 2026): newer Python SDK releases also expose a `streamable_http_client(url, http_client=httpx.AsyncClient(...))` form where you configure headers/timeout/auth on an `httpx.AsyncClient` (set `follow_redirects=True`). Use whichever your installed `mcp` version documents — `python -c "import mcp; print(mcp.__version__)"` then check that version's `docs/`. ---