Skip to main content
Glama

scratchpad-mcp

License: MIT Node MCP

AIエージェントのための永続的でトークン効率の良いストレージ。エージェントが毎回同じファイルを再読み込みしたり、同じコンテキストを再ロードしたりするのを防ぐMCPサーバーです。

agent: "what changed in this file since I last read it?"
server: { diff: [...], current_version: 14 }   ← not the whole file

なぜ必要なのか

エージェントはトークンを浪費します。すでに見たファイルを再読み込みし、すでに処理したドキュメントを再要約し、すでに計算した状態を再発見します。このサーバーは、それらの作業を保存し、モデルが低コストで推論できる形で後から取り出せる場所を提供します。

具体的には:

  • バージョン管理された書き込み: エージェントが作業中のドキュメントを保存し、「前回見たときから何が変わったか?」と尋ねると、サーバーは全文ではなく構造化された差分を返します。

  • 追記専用ログ: カーソルベースのページネーションにより、エージェントが自身の行動履歴を記録し、効率的に再生できます。

  • オンデマンド要約: 長いファイル(推定2000トークン以上)に対してClaude Haikuで生成され、ファイルバージョンごとにキャッシュされるため、変更のないファイルに対する繰り返しの要約呼び出しは無料です。

  • エージェントごとの名前空間: 1つのサーバーインスタンスで、状態を混在させることなく多数のエージェントをサポートできます。

ツール

すべてのツールは、最初の引数として agent_id を取ります。操作はそのエージェントの範囲内に限定され、エージェント同士が互いのファイルやログを読み取ることはできません。

ツール

機能

write_file(agent_id, path, content)

パスにコンテンツを保存します。書き込みのたびに自動的にバージョン管理され、最新の10バージョンが保持されます。

read_file(agent_id, path, since_version?)

全文、または前バージョンとのJSON行差分を読み取ります。since_version が削除されている場合、version_too_old: true を含む全文を返します。

append_log(agent_id, path, entry)

追記専用ログに1つのエントリを追加します。新しいエントリIDを返します。

read_log(agent_id, path, since_entry?)

カーソルページネーションを使用してログエントリを読み取ります。1ページあたり100エントリで、has_more フラグと last_entry_id カーソルが含まれます。

list_files(agent_id, prefix?)

ファイル(メタデータのみ)を一覧表示します。オプションでパスプレフィックスによるフィルタリングが可能です。

delete_file(agent_id, path)

ファイルとそのすべてのバージョン、およびキャッシュされた要約を削除します。

summarize_file(agent_id, path)

長いファイル(8000文字以上)をLLMで要約します。バージョンごとにキャッシュされるため、変更のないファイルへの繰り返し呼び出しはコストがかかりません。

get_usage_stats(agent_id)

エージェントの合計バイト数、ファイル数、ログ数、および合計操作数を返します。

差分フォーマット

since_version を指定した read_file は、チャンクのJSON配列を返します:

{
  "diff": [
    { "op": "equal",  "lines": ["line that didn't change"] },
    { "op": "remove", "lines": ["line that was deleted"] },
    { "op": "add",    "lines": ["line that was added"] }
  ]
}

行レベルの差分は意図的なものです。これはエージェントが最も確実に処理できる形式であり、ファイル全体を再処理するのではなく「何が変わったか」をエージェントが推論できるようにするためです。

パスルール

パスは [a-zA-Z0-9/_.-]+ に一致し、最大255文字、先頭に / は不可、.. シーケンスは不可です。エラー時には違反したルールが明示されます。

制限

  • ファイル書き込みあたり1MB

  • ログエントリあたり64KB

  • ファイルあたり10バージョン保持(古いものは自動的に削除)

  • read_log ページあたり100ログエントリ

インストール

Node 20以上とAnthropic APIキー(summarize_file のみで使用)が必要です。

git clone <this repo>
cd scratchpad-mcp
npm install
npm run build

これにより、実行可能なサーバーである dist/index.js が生成されます。

Claude Desktopでの設定

%APPDATA%\Claude\claude_desktop_config.json (Windows) または ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) に追加します:

{
  "mcpServers": {
    "scratchpad": {
      "command": "node",
      "args": ["C:\\path\\to\\scratchpad-mcp\\dist\\index.js"],
      "env": {
        "ANTHROPIC_API_KEY": "sk-ant-..."
      }
    }
  }
}

ANTHROPIC_API_KEYsummarize_file を呼び出す場合にのみ必要です。他の7つのツールはキーなしで動作します。

オプション: SCRATCHPAD_DB_PATH を設定してSQLiteの場所を上書きできます。デフォルトはプロジェクトルートの scratchpad.db です。

Claude Desktopを再起動してください。MCPサーバーリストに8つのツールが表示されるはずです。

セキュリティモデル — ホストする前に必ずお読みください

agent_idプレーンテキストのツールパラメータ です。認証はありません。呼び出し元は任意の agent_id を名乗ることができ、サーバーはそれを信頼します。これはV1では意図的な仕様であり、想定される以下のデプロイ形態では問題ありません:

  • サーバープロセスあたり1ユーザー。エージェントとSQLiteファイルは信頼境界を共有します。例:Claude Desktopインストール、Smitheryローカルインストール、ユーザーごとのApify Actor実行(Apifyはデフォルトで実行ごとに新しいコンテナと新しいデータベースファイルを生成します)。

以下の場合には 安全ではありません

  • マルチテナントスタンバイモード。1つのサーバープロセスが、同じSQLiteファイルを読み書きする複数の信頼できない呼び出し元にサービスを提供する場合。誰でも他の呼び出し元の agent_id を渡してデータを読み取ったり上書きしたりできます。

マルチテナント化が必要な場合は、ラッパー層で呼び出し元のAPIキーから agent_id を導出する(V2の計画)か、テナントごとに1つのプロセスを実行してください。

導入されている防御策

  • すべてのSQLはパラメータ化されており、パス、agent_id、プレフィックスを介したインジェクションは不可能です。

  • パスバリデーションにより、..、先頭の /、スペース、および [a-zA-Z0-9/_.-] 以外の文字は拒否されます。

  • list_files のプレフィックスマッチングは SUBSTR 等価性(LIKE ではない)を使用するため、SQLのワイルドカード _% は適用されず、マッチングは大文字と小文字を区別します。

  • 呼び出しごとのサイズ制限(ファイルあたり1MB、ログエントリあたり64KB)。

  • エージェントごとのクォータ(1000ファイル、10万ログエントリ、合計100MB)により、暴走したエージェントがホスト環境の共有ディスクを使い果たすことを防ぎます。

  • エラーは err.message のみを返し、スタックトレース、SQLiteパス、APIキーは含まれません。

summarize_file の費用は誰が負担するのか?

常に呼び出し元です。

  • ローカルインストール (Smithery, Claude Desktop, mcp.so): ユーザーは設定で自身の ANTHROPIC_API_KEY を提供します。ユーザーのPC、ユーザーのキー、ユーザーの請求となります。

  • Apifyホスト: すべてのActor実行は、実行ごとの入力から anthropicApiKey を読み取ります。.actor/entrypoint.sh ランチャーがサーバー起動前にそれを環境変数にマッピングします。各呼び出し元が自身の要約に対してAnthropicに支払いを行い、Actorの公開者はApifyの呼び出しごとの手数料のみを徴収します。

これをフォークしてホストする予定がある場合、Dockerfile、Apify Actor環境、または公開される設定ファイルにAPIキーをハードコード しないでください。他の7つのツールはキーなしで動作するため、設定しないことが安全なデフォルトです。

ストレージの仕組み

単一のSQLiteファイルですべてを保持します:

  • files(agent_id, path) ごとに1行、現在のバージョンを追跡します。

  • file_versions — バージョンごとの全文、ファイルごとに最新10件まで。削除は write_file ごとに行われます。

  • log_entries — 追記専用エントリ、変更不可。

  • summaries — ファイルごとの要約キャッシュ、バージョン不一致で無効化されます。

  • agent_usageget_usage_stats 用のエージェントごとの操作カウンター。

バージョン管理は(デルタではなく)バージョンごとの全文を保存します。これは書き込みを高速にし、読み取りを明確にするためです。差分は、2つのバージョンを行レベルの差分アルゴリズムにかけることで読み取り時に計算されます。コストは差分を要求した呼び出し元が負担し、書き込み側は負担しません。

ロードマップ

  • [ ] 呼び出しごとの課金のためのApifyパッケージング。

  • [ ] パラメータとして受け取るのではなく、APIキーから agent_id を導出する。

  • [ ] Postgresバックエンド(SQLiteスキーマは移植可能であるため、書き換えではなく接続先の切り替えとなります)。

  • [ ] エージェントごとのレート制限。

  • [ ] 操作の可視化のための構造化ログ。

ライセンス

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

A
license - permissive license
-
quality - not tested
C
maintenance

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/MikePressure/scratchpad-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server