Skip to main content
Glama
lukegskw

mcp-typescript-starter

MCP TypeScript Starter

TypeScript CI Container License

MCP TypeScript Starterは、TypeScriptでModel Context Protocolサーバーを構築するための、本番運用を意識した土台です。型付きのサンプルツールが1つ、stdioおよびStreamable HTTPトランスポート、厳格な検証、テスト、堅牢化されたコンテナ、そしてGHCRへの自動公開が含まれています。

クローンして、サンプルのドメインを置き換えれば、実際のMCPサーバーに必要なインフラを維持できます。

目次

Related MCP server: mcp-server-http-streamable

このスターターを使う

GitHubでUse this templateをクリックすると、独立したGit履歴を持つ新しいMCPサーバーを作成できます。作成後、スターターのカスタマイズに従って、サンプルツールを置き換え、プロジェクトのアイデンティティを更新してください。

プルリクエストを通じて改善を還元したい場合は、このリポジトリをフォークしてください。変更を送信する前にコントリビューションを参照してください。

このスターターが役に立ったなら、リポジトリにスターを付けていただけると幸いです。他のTypeScript開発者がこのプロジェクトを見つけやすくなります。

概要

このスターターは、検証済みのMCPツール定義から、クライアントから見える構造化された結果に至るまでの完全な経路を示しています。カスタムサーバーフレームワークではなく、現在のモジュール式MCP TypeScript SDKとHonoのWeb標準HTTPモデルを使用しています。

デフォルトのstdioトランスポートは、サーバーを子プロセスとして起動するローカルクライアント向けです。Streamable HTTPはステートレスで、リクエストごとに新しいMCPサーバーを作成するため、共有セッションストレージなしでレプリケーションできます。

この例は、上限付きのインメモリ処理を行います。テレメトリ、アプリケーションデータベース、永続ストレージ、認証、外部サービスへの依存はありません。

特徴

  • 厳格なZod入力・出力スキーマでツールを登録します。

  • 人間が読めるコンテンツと型付きの構造化コンテンツの両方を返します。

  • 正確なMCP安全性注釈を含みます。

  • stdioとステートレスなStreamable HTTPをサポートします。

  • DNSリバインディング対策のHost・Origin検証を備えたHonoを使用します。

  • HTTPをデフォルトでループバックにバインドし、他のインターフェースには許可リストを要求します。

  • ツール入力とHTTPリクエストボディを制限します。

  • stdioモードでは、stdoutをMCPプロトコルメッセージ専用に保ちます。

  • SIGINTとSIGTERMを冪等なグレースフルシャットダウンで処理します。

  • 読み取り専用ルートファイルシステムをサポートした非rootコンテナとして実行します。

  • 設定、stdio配線、MCP動作、Honoルート、実際のHTTPトラフィックをテストします。

  • 品質チェックを通過した場合のみ、マルチアーキテクチャイメージを公開します。

MCPツール

echo

検証済みのメッセージと任意の文字列メタデータをエコーします。ビジネスドメインを考案せずにMCPのスキーマ、登録、注釈、結果を学べるよう、意図的にシンプルにしています。

入力例:

{
  "message": "Hello, MCP!",
  "metadata": {
    "source": "example-client"
  }
}

構造化出力の例:

{
  "message": "Hello, MCP!",
  "metadata": {
    "source": "example-client"
  }
}

メッセージは10,000文字に制限されています。メタデータは最大20エントリまで受け付けます。キーは64文字、値は1,024文字に制限されています。

技術スタック

インストール

前提条件

  • ローカル開発にはNode.js 24+とpnpm 11。

  • コンテナデプロイにはDockerとDocker Compose。

Docker Compose

推奨されるHTTPデプロイでは、公開済みのマルチアーキテクチャイメージを使用します:

ghcr.io/lukegskw/mcp-typescript-starter:latest

Composeの例をダウンロードし、クライアントが使用するホスト名を指定してください:

curl -O https://raw.githubusercontent.com/lukegskw/mcp-typescript-starter/main/compose.example.yaml
export MCP_ALLOWED_HOSTS='mcp.example.internal'
docker compose -f compose.example.yaml up -d

Streamable HTTPエンドポイントとヘルスチェックエンドポイントは、次の場所で利用できます:

http://<host>:3000/mcp
http://<host>:3000/healthz

別のホストポートを公開するには、MCP_PUBLISHED_PORTを設定します。アプリケーションはコンテナ内では引き続きポート3000を使用します。

latestタグは、デフォルトブランチの最新の成功ビルドに追従します。管理されたデプロイとロールバックには、バージョンまたは不変のsha-*タグを使用してください。

Docker run

docker run -d \
  --name mcp-typescript-starter \
  --restart unless-stopped \
  --read-only \
  --user 10001:10001 \
  --cap-drop ALL \
  --security-opt no-new-privileges:true \
  --tmpfs /tmp:size=16m,mode=1777 \
  -e MCP_TRANSPORT=streamable-http \
  -e MCP_HOST=0.0.0.0 \
  -e MCP_ALLOWED_HOSTS=127.0.0.1,localhost,mcp.example.internal \
  -p 3000:3000 \
  ghcr.io/lukegskw/mcp-typescript-starter:latest

ソースからコンテナをビルドする

git clone https://github.com/lukegskw/mcp-typescript-starter.git
cd mcp-typescript-starter
docker buildx build --load -t mcp-typescript-starter:local .

ローカルでのNode.jsインストール

git clone https://github.com/lukegskw/mcp-typescript-starter.git
cd mcp-typescript-starter
pnpm install --frozen-lockfile
pnpm build
pnpm start -- --transport stdio

ローカルでのStreamable HTTP開発には:

MCP_TRANSPORT=streamable-http pnpm dev

設定

変数

必須

デフォルト

説明

MCP_TRANSPORT

いいえ

stdio

stdioまたはstreamable-http。

MCP_HOST

いいえ

127.0.0.1

HTTPバインドアドレス。

MCP_PORT

いいえ

3000

HTTP待受ポート。

MCP_ALLOWED_HOSTS

ループバック以外では必須

なし

カンマ区切りのHostおよびOriginホスト名許可リスト。

--transportコマンドラインオプションはMCP_TRANSPORTを上書きします。MCP_ALLOWED_HOSTSにはURLではなくホスト名を指定します。正当なクライアントとヘルスチェックが使用するすべてのホスト名を含めてください。

サーバーのサンプル設定にはシークレットは含まれていません。ドメインの認証情報は、デプロイプラットフォームまたは環境変数を通じて追加してください。MCPツールの引数やコミットされたファイルとして決して追加しないでください。

MCPクライアントのセットアップ

Streamable HTTPサーバー定義を受け付けるクライアントの場合:

mcp_servers:
  starter:
    url: http://127.0.0.1:3000/mcp

ローカルのstdioサーバーを起動するクライアントの場合:

{
  "mcpServers": {
    "starter": {
      "command": "node",
      "args": [
        "/absolute/path/to/mcp-typescript-starter/dist/main.js",
        "--transport",
        "stdio"
      ]
    }
  }
}

ローカルクライアントにstdio経由でコンテナを起動させるには、docker run -i --rmを使用し、イメージ名の後に--transport stdioを渡します。クライアントが標準入力と標準出力でMCPメッセージを交換できるよう、-iが必要です。

クライアントの設定形式は異なります。正確なスキーマについてはクライアントのドキュメントを参照し、サーバー定義を変更した後はクライアントを再起動または再読み込みしてください。

スターターのカスタマイズ

主な拡張ポイントは意図的に直接的です:

  1. src/tools/echo.tsをコピーまたは置き換えます。

  2. ハンドラーを書く前に、厳格な入力・出力スキーマを定義します。

  3. src/server.tsでツールを登録します。

  4. MCPの動作テストと、該当するドメインの統合テストを追加します。

  5. パッケージ名、サーバーのアイデンティティ、イメージ参照、READMEの内容を置き換えます。

ツールモジュールは、自身のスキーマとハンドラーに責任を持たせてください。トランスポートモジュールはドメインツールから独立させてください。サービスや永続化は、実際の動作で必要になった場合にのみ導入してください。

検証

リポジトリの完全なテストスイートを実行します:

pnpm install --frozen-lockfile
pnpm format:check
pnpm lint
pnpm typecheck
pnpm test:unit
pnpm test:integration
pnpm build

コンテナの変更の場合:

docker buildx build --load -t mcp-typescript-starter:test .

最後に、MCPクライアントを接続し、echoが一覧に表示され、テキストと構造化コンテンツの両方を返すことを確認します。HTTPモードでは、/healthzが{"status":"ok"}を返すことを確認します。

制限事項

  • この例では1つのツールのみを公開し、リソースやプロンプトはありません。

  • Streamable HTTPには認証がありません。ループバック、信頼できるLAN、VPN、プライベートコンテナネットワーク、または認証付きリバースプロキシに限定してください。

  • HostおよびOriginの許可リストは、一部の種類のDNSリバインディング攻撃を防ぎますが、呼び出し元を認証するものではありません。

  • HTTPサーバーはステートレスで、共有の永続化や分散調整は含まれていません。

  • レート制限、トレーシング、メトリクス、ドメイン固有のロギングは含まれていません。

  • このリポジトリはソーススターターであり、公開されたnpmライブラリではありません。

HTTPトランスポートを公開する前、またはセキュリティ問題を報告する前に、SECURITY.mdを確認してください。

コントリビューション

コントリビューションを歓迎します。プルリクエストを開く前に:

pnpm install --frozen-lockfile
pnpm format:check
pnpm lint
pnpm typecheck
pnpm test
pnpm build
docker buildx build --load -t mcp-typescript-starter:test .

変更は、厳格な型付け、上限付きの検証、構造化されたMCP結果、stdoutのプロトコル純粋性、安全なHTTPデフォルト、決定論的なテスト、ユーザーに見える動作のドキュメントを維持しなければなりません。具体的なユースケースのない抽象化は追加しないでください。

ライセンス

MIT。LICENSEを参照してください。

Available Tools

1 tool
echoEchoB
Read-onlyIdempotent

Echo a validated message and optional string metadata.

NameRequiredDescriptionDefault
messageYes
metadataNo

Output Schema

NameRequiredDescription
messageYes
metadataNo

TDQS

B3.2/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, covering safety and side-effect expectations. The description adds minimal behavioral context, mainly 'validated', which hints that inputs are checked but not how. No contradiction with annotations; the bar is lower, so a 3 is appropriate.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, direct sentence with no unnecessary words. The verb is front-loaded, and the optional part is clearly flagged. Every word earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a trivial echo tool, the description is nearly sufficient. The output schema exists, and annotations cover read-only/idempotent behavior, so return-value details are not needed. The only gap is vague 'validated' wording, but the tool is simple enough that an agent can invoke it correctly with the given information.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate. It names 'message' and 'optional string metadata', but the schema already provides types and constraints. Calling metadata 'string metadata' is potentially misleading because the schema defines metadata as an object with string values, not a string. This adds little value beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses a specific verb ('echo') and resource ('a validated message and optional string metadata'), making the core function clear. There are no sibling tools to differentiate from, so the lack of distinction is not a flaw. However, 'validated' is slightly ambiguous — it might imply an extra validation step that is actually handled by the schema.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance is given on when to use this tool or what to prefer it over. There are no siblings, but the description still does not state typical scenarios (e.g., debugging, round-trip testing). The intended usage is only implied by the verb 'echo'.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 1 tool updatev0.1.0
    • First observedecho

TDQS

B3.4/5.0

Scored across 1 tool

Disambiguation5/5

With only one tool, there is no possibility of confusion or overlap. The single 'echo' tool is clearly distinct by virtue of being the only tool available.

Naming Consistency5/5

The single tool name 'echo' is short, clear, and directly describes its function. Since there is only one tool, naming consistency is trivially satisfied.

Tool Count3/5

One tool feels minimal even for a starter server, but it is a common pattern for a simple template. The count is at the lower edge of being acceptable rather than egregiously insufficient.

Completeness2/5

The server only provides an echo function, which is useful for testing connectivity but lacks any real domain operations. There are no CRUD or workflow capabilities, representing a significant gap for any practical use beyond a basic demo.

Maintenance

ActivitySlowing
ResponsivenessNo issues

Related MCP Connectors

Related MCP Servers

  • A
    license
    Not graded
    quality
    D
    maintenance
    A minimal Model Context Protocol server that facilitates network-based client connections using Streamable HTTP transport. It provides a greeting tool and is optimized for consistent deployment across local environments, Docker, and Kubernetes.
    MIT
  • A
    license
    Not graded
    quality
    B
    maintenance
    Provides a production-ready Model Context Protocol server with dual STDIO and Streamable HTTP transports, enabling file operations, memory, database queries, RAG, web search, GitHub integration, background tasks, and prompt-based workflows.
    MIT