@nogataka/claude-code-proxy-ts
v0.0.4
Published
> **Quick Start** > ```bash > npx @nogataka/claude-code-proxy-ts@latest --config ~/.claude-code-proxy-ts/config.json > ``` > 初回は設定ファイルが自動生成されます。`--config` を省略しても `~/.claude-code-proxy-ts/config.json` にテンプレートが作成されるため、API キーとモデルを追記してご利用ください。
Readme
Claude Code Proxy (TypeScript)
Quick Start
npx @nogataka/claude-code-proxy-ts@latest --config ~/.claude-code-proxy-ts/config.json初回は設定ファイルが自動生成されます。
--configを省略しても~/.claude-code-proxy-ts/config.jsonにテンプレートが作成されるため、API キーとモデルを追記してご利用ください。
Claude Code Proxy (TypeScript版) は、Anthropic Claude Code API 互換のリクエストを OpenAI / Azure OpenAI / Anthropic など複数プロバイダーへルーティングする Fastify + TypeScript 製プロキシです。Claude 形式の SSE ストリーミング、ツール呼び出し、マルチモーダル入力をサポートし、単一の設定ファイルで各プロバイダーの資格情報を管理できます。
Table of Contents
Overview
/v1/messagesを Claude 形式で受け取り、プロバイダー毎の Chat Completions API へ転送- OpenAI / Azure OpenAI / Anthropic など複数プロバイダーを JSON 設定で切り替え
- Claude スタイルの SSE (
message_start,content_block_deltaなど) をストリーミングで返却 - 任意のクライアント API キー検証、詳細なエラーメッセージ、ヘルスチェック・接続テストを提供
Usage Guide
要件の準備
Node.js 20 以上と pnpm 8 以上を用意します。未インストールの場合は以下を実行してください。corepack enable # Node.js 20 では pnpm が同梱されています corepack prepare [email protected] --activateリポジトリの取得
git clone https://github.com/nogataka/claude-code-proxy-ts.git cd claude-code-proxy-ts pnpm install設定ファイルの生成
初回はテンプレートを生成してから内容を編集します。任意のパスを指定して生成すると差分確認がしやすくなります。pnpm start -- --config ./config.local.json # 生成後にサーバーはそのまま終了させて構いません設定の編集
生成された JSON を開き、各プロバイダーのapiKey、baseUrl、モデルマッピング (models.big/middle/small) を実運用値に書き換えます。- Azure を使う場合は
baseUrlに/deployments/を含めず、models.bigなどにデプロイメント名を指定します。 - クライアントからのアクセス制限を行う場合は
client.expectedApiKeyに共有キーを設定し、x-api-keyヘッダー経由で提示させてください。
- Azure を使う場合は
サーバーの起動
開発中はホットリロード付きで起動し、本番相当で動かすときはstartスクリプトを使用します。pnpm dev # 開発用途 # もしくは pnpm start # 本番相当(tsx を介さず実行)動作確認
起動後にヘルスチェックと接続テストで疎通を確認します。curl http://localhost:8082/health curl http://localhost:8082/test-connectionクライアントから利用
Claude CLI や任意の HTTP クライアントから以下のようにベース URL を指定します。Claude CLI 側でv1/messagesが付与されるため、ここではホスト名のみを設定してください。# 既定プロバイダー (openai) ANTHROPIC_BASE_URL=http://localhost:8082 claude # Azure / Ollama / Databricks へ切り替えたい場合 ANTHROPIC_BASE_URL=http://localhost:8082/azure claude ANTHROPIC_BASE_URL=http://localhost:8082/ollama claude ANTHROPIC_BASE_URL=http://localhost:8082/databricks claudeOpenAI / Codex 互換クライアントからは
/v1/chat/completionsエンドポイントをそのまま利用できます。ルートopenai・azure・ollamaで同一の OpenAI SDK を介して処理されるため、特別な変換は不要です。API リクエストの検証
ログレベルをconfig.jsonのlogLevelで調整し、debugにすると変換されたリクエスト/レスポンスがstdoutに出力されます。問題があればpnpm lintやCI=1 pnpm test -- --runで品質ゲートを通過していることを確認してください。
Directory Layout
claude-code-proxy-ts/
├── README.md
├── package.json / pnpm-lock.yaml
├── tsconfig.json / vitest.config.ts
├── config.json (sample)
├── src/
│ ├── main.ts # Fastify エントリポイント
│ ├── api/endpoints.ts # HTTP ルーティング
│ ├── conversion/
│ │ ├── request_converter.ts # Claude → Provider 変換
│ │ └── response_converter.ts # Provider → Claude (同期 & ストリーミング)
│ ├── core/
│ │ ├── config.ts # JSON 設定ローダー
│ │ ├── client.ts # Provider クライアント (OpenAI / Azure)
│ │ ├── logging.ts # ログレベル管理
│ │ └── model_manager.ts # Claude モデル → Provider モデル変換
│ ├── models/ # Zod スキーマ & 型定義
│ └── core/constants.ts # ロール / イベント定数
├── tests/
│ ├── setup.ts # テスト用設定ファイル生成
│ ├── conversion.test.ts # リクエスト変換テスト
│ ├── response_converter.test.ts # SSE 変換テスト
│ └── client.test.ts # エラー分類テストKey Features
- エンドポイント:
/v1/messages,/:providerId/v1/messages,/v1/messages/count_tokens,/health,/test-connection - マルチプロバイダー対応: JSON 設定で API キー / ベース URL / モデルを切り替え、
/:providerIdプレフィックスで明示的に選択 - Claude ↔ Provider 変換: システムプロンプト・ツール呼び出し・マルチモーダル入力・停止シーケンスを忠実に変換
- SSE ストリーミング: 中断検知付きで Claude イベントを逐次送出、ツール引数 JSON のインクリメンタル転送に対応
- 公式 Ollama サポート:
ollamaSDK を用いてチャット/ストリーミング/structured output を処理し、OpenAI 互換のツール呼び出しもマッピング - OpenAI Chat Completions API:
/v1/chat/completionsを追加し、OpenAI/Azure/Ollama を OpenAI SDK 経由でそのまま中継 - Azure サポート:
apiVersion・deploymentを指定すると Azure OpenAI クライアントに自動切替 - セキュリティ / 観測性: クライアント API キー認証、詳細なエラーログ、疎通テスト API を同梱
Architecture
Fastify (src/main.ts)
→ registerApiRoutes (src/api/endpoints.ts)
→ Claude リクエスト検証 (Zod)
→ convertClaudeToOpenAI (request_converter.ts)
→ Provider Client (core/client.ts)
→ OpenAI | AzureOpenAI
→ convertOpenAIToClaudeResponse / convertOpenAIStreamingToClaudeWithCancellation
→ fastify-sse-v2 で SSE 配信- AbortController でストリーミング中のキャンセルを管理
- Usage トークン情報やエラー内容を Claude 形式へ再構築
getConfig()は初回アクセス時に~/.claude-code-proxy-ts/config.jsonを生成・キャッシュ
Getting Started
- 依存関係のインストール
pnpm install - 設定ファイルを用意
初回起動時に設定ファイルが存在しない場合、pnpm start -- --config ./config.json # 任意パスを渡すと指定先を生成~/.claude-code-proxy-ts/config.json(もしくは--configで指定したパス) がテンプレート付きで生成されます。API キーやモデル名を編集してください。 - 開発モードで起動
pnpm dev # tsx watch src/main.ts - プロダクション相当で起動
pnpm start # node --import tsx src/main.ts - Claude CLI からプロキシを指定
ANTHROPIC_BASE_URL=http://localhost:8082 claude # プロバイダー個別指定: http://localhost:8082/azure など
npx でのワンライナー起動
npx @nogataka/claude-code-proxy-ts@latest --config ~/.claude-code-proxy-ts/config.json--config を省略するとデフォルトの ~/.claude-code-proxy-ts/config.json を利用します。
Configuration
設定は JSON ファイル 1 つで管理します。サンプル構造:
{
"logLevel": "warning",
"server": { "host": "0.0.0.0", "port": 8082 },
"limits": { "maxTokens": 4096, "minTokens": 256, "requestTimeoutSec": 90, "maxRetries": 2 },
"client": { "expectedApiKey": "" },
"providers": {
"openai": {
"adapter": "openai",
"apiKey": "sk-...",
"baseUrl": "https://api.openai.com/v1",
"models": { "big": "gpt-4o", "middle": "gpt-4o", "small": "gpt-4o-mini" }
},
"anthropic": {
"adapter": "openai",
"apiKey": "anthropic-...",
"baseUrl": "https://api.anthropic.com/v1",
"models": { "big": "claude-3-opus", "middle": "claude-3-sonnet", "small": "claude-3-haiku" }
},
"azure": {
"adapter": "azure",
"apiKey": "azure-...",
"baseUrl": "https://<resource>.openai.azure.com/",
"models": { "big": "gpt-4o", "middle": "gpt-4o", "small": "gpt-4o-mini" },
"azure": { "apiVersion": "2024-05-01-preview", "deployment": "gpt4o" }
},
"ollama": {
"adapter": "ollama",
"baseUrl": "http://localhost:11434",
"models": { "big": "llama3.1", "middle": "llama3", "small": "llama3.1:8b" },
"options": { "path": "/api/chat", "stream": true }
},
"databricks": {
"adapter": "databricks",
"baseUrl": "https://adb-<workspace>.azuredatabricks.net",
"models": { "big": "databricks-claude-sonnet-4" },
"options": {
"path": "/serving-endpoints/databricks-claude-sonnet-4/invocations",
"headers": {
"Content-Type": "application/json",
"Authorization": "Bearer YOUR_DATABRICKS_TOKEN"
},
"stream": false
}
}
},
"routing": { "defaultProvider": "openai", "fallbackOrder": ["azure", "ollama", "databricks"] }
}providersキーは任意の ID を付与可能 (openai,azure,ollama,databricksなど)。/:providerIdプレフィックスで選択します。adapterで呼び出し方式を指定します。openai(デフォルト) /azure/ollama/databricksをサポート。options.pathでベース URL に連結する相対パス、options.headersで追加ヘッダーを定義できます。options.streamをtrueにするとアダプター側でストリーミングを要求します(ollama用)。- Azure の
baseUrlには/deployments/を含めず、models.big/middle/smallに設定した値を Azure デプロイメント名として扱います (モデル未指定の場合はbigを使用)。 client.expectedApiKeyを設定すると、クライアントはx-api-keyか Bearer トークンで同キーを提示する必要があります。limits.maxTokens/minTokens/requestTimeoutSec/maxRetriesは共通デフォルトを制御。Azure のapiVersionが 2024-05-01 以降ならmax_completion_tokensを利用します。
Model Mapping
/v1/messages(Claude 互換ルート)では、リクエストに含まれる Claude モデル名をmodel_managerがproviders.<id>.models.{small|middle|big}の優先順位に従って変換してからプロバイダーへ送信します。例:haiku → small → middle → big、sonnet → middle → big → small、opus → big → middle → small。該当がなければbig → middle → smallの順に探索します。- プロバイダーがどのモデルで応答しても、Claude クライアントへ返すレスポンスには元の Claude モデル名が保持されます。
/v1/chat/completions(OpenAI/Codex 互換ルート)ではマッピングを行わず、クライアントが指定したmodelをそのまま OpenAI SDK(OpenAI/Azure/Ollama 共通)に渡します。
Adapter の挙動
openai: OpenAI / Anthropic など Chat Completions 互換 API を想定。既存の変換・ストリーミング処理が利用されます。azure: OpenAI 互換に加えてazure.apiVersion/deploymentを使った Azure OpenAI 呼び出し。ollama: 公式ollamaJS SDK 経由でローカル Ollama に接続。baseUrlを指定するだけでチャット/ストリーミング/ツール呼び出し/構造化出力(JSON スキーマ)まで動作します。databricks: Databricks Serving Endpoints など OpenAI 互換 REST API を呼び出します。options.pathやoptions.headersでエンドポイント/トークンを指定し、options.stream: falseにすると完全同期モードになります。
Development Workflow
- 起動:
pnpm dev(ホットリロード) /pnpm start(本番モード) - Lint:
pnpm lint - Format:
pnpm format - ビルド:
pnpm build - ログレベル:
config.jsonのlogLevelをdebug/info/warning/error/criticalから選択 - Config リフレッシュ: テストや再読み込みが必要な場合は
resetConfigForTesting()/resetOpenAIClient()を利用 (tests/setup.tsで自動実行)
Testing
CI=1 pnpm test -- --runVitest が JSON 設定を一時ディレクトリに生成してから各テストを実行します。ストリーミング変換・エラー分類・リクエスト変換の回帰テストが含まれます。
Roadmap
- End-to-End HTTP Tests: Fastify サーバーを立ち上げた実運用経路の自動テスト
- 拡張プロバイダーサポート: Ollama や他社互換 API へのドライバ追加
- デプロイメント支援: Dockerfile / Helm Chart の提供
- Metrics & Tracing: OpenTelemetry など観測基盤への出力
- Config UI: 設定 JSON の編集を支援する簡易 CLI / UI
バグ報告・機能要望・プルリクエストは歓迎しています。
