mcpField
C
chembl-mcp-server

chembl-mcp-server

リモート
github.com/cyanheadsヘルスケア14 日前に更新
リポジトリ

chembl-mcp-server について

chembl-mcp-serverは、創薬研究者にChEMBLの化合物、標的、生物活性、医薬品情報を提供します。化合物とタンパク質標的を結び付け、測定された活性を順位付けできるほか、ステージングした生物活性データを読み取り専用SQLで分析できます。

主な機能

  1. 01名称、ID、構造による化合物検索
  2. 02タンパク質標的と遺伝子標的の特定
  3. 03生物活性測定値の絞り込みと順位付け
  4. 04医薬品の作用機序と適応症の取得
  5. 05読み取り専用SQLによるステージングデータの検索

活用シーン

  1. 01SMILES構造から化合物を検索
  2. 02化合物と標的の組み合わせで活性を比較
  3. 03医薬品の作用機序と適応症を確認
  4. 04ステージングした生物活性データ行を集計

MCP 対応

MCPクライアントにChEMBL検索・分析ツールと化合物・標的リソースを提供します。STDIOとStreamable HTTPに対応します。

設定

リモートサーバーはインストール不要です。クライアントを選んで設定をコピーするか、ワンクリックで導入できます。

エンドポイントhttps://chembl.caseyjhand.com/mcp
インストールコマンドをコピー
Claude CodeTerminal
Cursor.cursor/mcp.json
VS Code.vscode/mcp.json
Claude Desktopclaude_desktop_config.json
Windsurf~/.codeium/windsurf/mcp_config.json

コマンドはターミナルで実行し、JSON は各クライアントの MCP 設定に貼り付けて再起動します。認可が必要なサーバーは初回接続時にログインを求めます。

パッケージ
npm@cyanheads/chembl-mcp-server0.4.1

ツール

7
パラメーター型必須説明
limitintegerいいえ返す分子の最大数です。省略した場合はサーバーの既定値(25)になります。
querystringいいえsearch_type=name で使う検索テキストです。薬剤名、ChEMBL ID、または InChIKey を指定します。例:"imatinib"、"CHEMBL25"。
cursorstringいいえ前回の呼び出しの nextCursor から得られる不透明な継続トークンです。前のページの続きから再開します。最初のページでは省略してください。トークンを生成したときと同じクエリ/構造/フィルターを再送してください(変更できるのは limit のみで、このページのサイズを指定します)。異なるフィルターに適用すると、別の結果セットをたどります。
structurestringいいえ構造検索に使う SMILES 文字列です。例:"CC(=O)Oc1ccccc1C(=O)O"。search_type が exact/similarity/substructure の場合に必須です。
search_typeenumいいえname = テキスト検索(query);exact = 完全な構造一致;similarity = Tanimoto ≥ 閾値;substructure = 指定構造を含むもの。すべての構造モードで `structure` が必要です。name | exact | similarity | substructure
max_phase_minintegerいいえsearch_type=name の場合、この最大臨床フェーズ以上の化合物に絞り込みます(例:4 なら販売中の医薬品のみ)。
similarity_thresholdintegerいいえsearch_type=similarity の最低 Tanimoto 類似度(%)です(40~100。ChEMBL は 40 未満を受け付けません)。他のモードでは無視されます。

詳細

@cyanheads/chembl-mcp-server

MCP を介して ChEMBL の化合物とタンパク質ターゲットを関連付け、生物活性(IC50/Ki/EC50)を順位付けし、医薬品の作用機序と適応症を検索します。STDIO または Streamable HTTP に対応しています。

7 個のツール(オプトインで +1) • 2 個のリソース

Version License Docker MCP SDK npm TypeScript Bun

Install in Claude Desktop Install in Cursor Install in VS Code

Framework

公開ホストサーバー: https://chembl.caseyjhand.com/mcp


概要

ChEMBL(EBI)の創薬データです。化合物、タンパク質ターゲット、測定された生物活性(IC50/Ki/EC50)を関連付けた厳選データに加え、医薬品の作用機序と適応症を収録しています。化合物を名前、ID、または構造で検索し、ターゲットを特定して、最も高い効力を示す測定値を順位付けできます。

ツール
ツール説明
chembl_search_molecules化合物を名前/ChEMBL ID/InChIKeyで検索するか、SMILESから構造検索(完全一致 | 類似性 | 部分構造)を実行します。
chembl_get_bioactivities化合物(またはその全形態群)、標的、あるいは両方(化合物×標的のペア)の生物活性測定値を取得する、主要な化合物↔標的連携ツールです。pchembl_valueの順に並べるか、potency_viewを使って値のない測定値を取得します。大量の結果はキャンバスに出力されます。
chembl_search_targetsタンパク質/遺伝子シンボル/UniProtアクセッションを、chembl_get_bioactivitiesで必要となるChEMBL標的IDに対応付けます。
chembl_get_drug_info薬剤の薬理情報(作用機序、分子標的、作用の種類、初回承認年、臨床適応症)を、薬剤の塩やその他の代替形態も含めて取得します。
chembl_get_assay生物活性の各行の根拠となるアッセイ情報(種類、標的、生物種、ChEMBLの1~9の信頼度スコア)を取得します。
chembl_dataframe_queryキャンバスにステージングされた生物活性の行に対して、読み取り専用のSQL SELECTを実行し、全件を対象に並べ替え、グループ化、重複排除、集計を行います。
chembl_dataframe_describeキャンバスにステージングされたテーブルと列を一覧表示するため、クエリの前に正しいSQLを作成できます。
chembl_dataframe_dropキャンバスから、名前を指定したステージング済みテーブルを削除します。CHEMBL_DATAFRAME_DROP_ENABLED=trueで有効化します。有効でない場合はtools/listに表示されません。TTLによってステージング済みテーブルはすでに回収されるためです。
リソース
リソース説明
chembl://molecule/{chemblId}ChEMBL IDによる分子レコードです。chembl_search_moleculesの行と同じ形式です。
chembl://target/{chemblId}ChEMBL標的IDによる標的レコードです。優先名、種類、生物種、構成要素のUniProtアクセッションと遺伝子シンボルを含みます。

すべてのリソースデータはツール経由でも取得できるため、ツールのみを利用するMCPクライアントでも情報を失いません。プロンプトはありません。標準的なワークフローはエージェントが直接組み合わせる短いツールチェーンであり、サーバー間の連携手順はサーバーレベルのinstructionsとして提供されます。

機能リファレンス

chembl_search_molecules ツール
  • デフォルトのsearch_type=nameでは、薬剤名、別名、ChEMBL ID、InChIKeyを1回のクエリで検索します。クエリがChEMBL IDまたはInChIKeyと完全に一致する場合、あいまい検索用のテキストインデックスではなく、ChEMBLの単一レコード検索に振り分けられます(totalCount: 1)。
  • search_typeで構造検索を指定できます。exactは完全一致、similarityは類似性(Tanimoto ≥ similarity_threshold。整数の40~100、デフォルトは70)、substructureは部分構造検索です。structureにはSMILESを指定します。max_phase_min(名前検索のみ)を使うと、最大臨床フェーズが指定値以上の化合物に絞り込めます。ChEMBLが解析できないSMILESを指定した場合、類似性検索または部分構造検索の最初のリクエストで、サービス停止ではなくinvalid_structureエラーになります。
  • 各行にはmax_phase、MW、AlogP、Lipinskiのルール・オブ・ファイブ違反数、QEDが含まれます。Tanimotoのsimilarity割合が含まれるのはsearch_type=similarityの結果のみです。他のモードではnullではなく、省略されます。
  • 各行には、その化合物群の親を示すparent_chembl_idも含まれます。ERLOTINIB HYDROCHLORIDE(CHEMBL1079742)の親はCHEMBL553で、記録された階層がない化合物は自身を親として示します。塩は親化合物より上位に並ぶことがありますが、化合物群全体の測定値に占める割合は小さい場合があります。
  • nextCursor/cursorを使ってページネーションします。最後のページではnullではなく省略されます。カーソルを使用するときは、カーソルの生成時と同じフィルターを指定してください。limitが100を超える場合は100件で返され、通知が表示されます。
  • ChEMBLでは、名前検索の件数カウントとページネーションは一致数10,000件、部分構造検索は30,000件で打ち切られます。この上限に達すると、totalCountCapped: trueと、その件数以上が一致し残りには到達できない旨の通知が返されます。上限未満になるようにクエリを絞り込んでください。
  • molecule_chembl_idをchembl_get_bioactivitiesまたはchembl_get_drug_infoに渡して連携します。

chembl_get_bioactivities ツール
  • molecule_chembl_id または target_chembl_id の少なくとも一方を指定してください。両方を指定すると、その化合物とターゲットのペアに絞り込まれます。どちらも指定しない場合は missing_filter エラーになります
  • include_alternate_forms: true を指定すると、molecule_chembl_id の対象がファミリー全体に広がります。ファミリーには親化合物と、ChEMBL がその下に登録しているすべての塩およびその他の代替形態が含まれます(イマチニブ CHEMBL941 は単独で4,878件、各形態を合わせると5,802件の測定値があります)。塩の ID を指定しても同じファミリーが対象になり、各行には測定対象となった形態が保持されます。件数、両方のビュー、カーソルページ、スピルでは同じファミリーが使用されます。カーソルを使う場合は、このフラグも再指定してください。molecule_chembl_id を指定せずにこのフラグを使うと、alternate_forms_without_molecule エラーになります
  • ID は正規形に照合されます。"chembl941" と " CHEMBL941 " は CHEMBL941 として扱われ、ChEMBL ID ではない値("imatinib")を指定すると、リクエストを送信する前に -32602 が返され、検索ツールに誘導されます。molecule_chembl_id の場合、include_alternate_forms が無効であれば、値はそのままフィルターに渡されます
  • standard_type(IC50/Ki/EC50/…)、pchembl_value_min、assay_type、organism、variant で絞り込みます。pchembl_value の値で順位付けします。この値を比較できるのは、同じ standard_type 内に限られます
  • assay_type にはコード(B/F/A/T/P/U)または ChEMBL での名称(binding、ADMET、…)を、大文字と小文字を問わず指定できます。standard_type は大文字と小文字を区別して完全一致します。ChEMBL には大文字と小文字だけが異なる別個のタイプ(Kd/KD)が登録されています。一致するものがない場合、通知には同じフィルター条件で ChEMBL に記録されている大文字・小文字違いのタイプが示されます("ic50" → IC50)
  • variant を指定すると、野生型と変異型の効力を分けられます。"wild_type" は変異の記録がない測定値を返し、それ以外の値は記録された変異全体に対して大文字と小文字を区別せずに照合されます("T315I"、"F508del"、ChEMBL の順序で記録された "L858R,T790M"、"UNDEFINED MUTATION")。"L858R" だけでは "L858R,T790M" に一致しません
  • 各行には activity_comment(例:Not Active。値が測定されなかった場合、唯一の結果となることもよくあります)と data_validity_comment(例:Outside typical range)、アッセイの assay_variant_mutation と assay_variant_accession、引用用の出典である document_chembl_id と document_year が含まれます
  • potency_view で potency_ranked(デフォルト。導出可能な pchembl_value がある測定値)または null_potency(除外された行)を選択します。null_potency と pchembl_value_min を併用すると contradictory_potency_filter エラーになり、totalCount は両方のビューの合計です
  • 数値はサービス境界で number | null に変換されます。効力の値がない場合は 0 ではなく null になります
  • 大きなデータセットは、ビューごとに DataCanvas テーブル(bioactivities/bioactivities_null_potency)にスピルされます。キャンバスはデフォルトで有効で、CANVAS_PROVIDER_TYPE=none に設定すると無効になります
  • スピルでは、ページを CHEMBL_MAX_CONCURRENT_PAGES 件ずつ取得します(デフォルトは4)。行数上限 CHEMBL_MAX_SPILL_ROWS(デフォルトは50,000)と時間制限 CHEMBL_SPILL_DEADLINE_MS(デフォルトは45秒)の範囲内で処理されます。どちらかの上限に達してビュー全体を処理できなかった場合、レスポンスには truncated: true、staged_row_count、truncated_by(row_cap または time_budget)が含まれます
  • インラインプレビューの上限は、スピルの状態にかかわらず常に limit(デフォルトは25)です。limit が1,000を超える場合は1,000件まで返され、通知が表示されます
  • ビューがスピルされる場合に限りキャンバスが作成されるため、インラインに収まる場合はキャンバスが作成されません。返された canvas_id を渡すと、その後のカーソルを使わない呼び出しごとに、そのビューのテーブルが呼び出し独自の行で再ステージされます。行がインラインに収まる場合や、一致する行がない場合も同様です。これにより以前の行は置き換えられますが、もう一方のビューのテーブルはそのままです。スピルによるテーブルの置き換えは、スピルが成功した場合に限られます。そのため、失敗またはキャンセルされた場合は以前の行が残ります。テナントごとのキャンバス上限に達しているときに canvas_id なしでスピルすると、canvas_capacity_exhausted エラーになります
  • 呼び出しで何もステージされない場合(キャンバスが無効、または canvas_id なしでビューがインラインに収まる場合)、ビューは nextCursor/cursor を使って1ページずつ返されます。最後のページでは null ではなく省略されます。カーソルは、発行時と同じフィルターおよび potency_view を指定して使用してください。カーソルページはインラインで返され、キャンバスが有効でもステージされません

chembl_search_targets tool
  • accession(UniProt、例:P00533)、gene_symbol、query(フリーテキスト)のいずれかを少なくとも1つ指定し、organism と target_type で絞り込みます。いずれも指定しない場合は missing_input エラーになります
  • 最も正確な入力は UniProt アクセッションです。uniprot/protein サーバーから連携してください。accession と target_type は大文字に変換して照合され、ChEMBL の記録形式に合わせます("p00533" は P00533 として、"single protein" は SINGLE PROTEIN として扱われます)。gene_symbol と organism は大文字と小文字を区別せずに照合されます
  • 各行には、ChEMBL のネストされたコンポーネント同義語からフラット化した、ターゲットタイプ、生物種、コンポーネントの UniProt アクセッションと遺伝子シンボルが含まれます
  • nextCursor/cursor を使ったページネーションに対応しており、limit の上限処理を含め、chembl_search_molecules と同じ仕様です
  • target_chembl_id を chembl_get_bioactivities に連携してください

chembl_get_drug_info tool
  • molecule_chembl_id(大文字と小文字は問いません)または分子の標準 InChIKey を指定します。作用機序、分子標的、作用タイプ、初回承認年、およびそれぞれに到達した最高フェーズを含む臨床適応症を返します
  • 両方のリストは parent_molecule_chembl_id で示される医薬品ファミリーを対象とします。ChEMBL では、医薬品の作用機序や承認済み適応症が塩に記録されることが多いためです。エルロチニブ CHEMBL553 とその塩酸塩は、同じ EGFR 作用機序を返します。この作用機序は CHEMBL1079742 に記録されています。各作用機序には、記録された剤形が示されます。各適応症は MeSH/EFO の組み合わせごとに、いずれかの剤形が到達した最高フェーズで1回だけ表示され、各剤形についてはそれぞれのフェーズが記載されます(ソラフェニブの肝細胞癌は、トシル酸塩 CHEMBL1200485 ではフェーズ4、重水素化類縁体のドナフェニブ CHEMBL4297490 ではフェーズ2です)
  • まず分子レコードを取得し、取得に失敗すると呼び出し全体が失敗します。その後、作用機序と適応症を Promise.allSettled で取得するため、いずれかのリストの取得に失敗しても呼び出し全体は失敗せず、部分的な結果としてその旨が明示されます
  • 各リストには、それぞれの *_total_count と並んで mechanisms_status/indications_status(complete/truncated/failed)が含まれます。空の配列が確定的な結果となるのは、ステータスが complete の場合に限ります。取得に失敗したリストの *_failure には、時間切れ(timeout)か、ChEMBL がエラーを返したか(upstream_error)が示されます。適応症リストが切り詰められた場合は indications_rows_fetched が返され、不足している適応症の件数の範囲がわかります。表示されたフェーズと剤形は下限値です
  • 作用機序の target_chembl_id を chembl_get_bioactivities に連携できます

chembl_get_assay tool
  • chembl_get_bioactivities の行にある assay_chembl_id を、大文字と小文字を問わず指定します。ChEMBL ID ではない値を指定すると、リクエストを送信する前に -32602 で失敗します
  • 説明、アッセイタイプ(結合/機能/ADMET/毒性)、測定対象のターゲット、生物種、ChEMBL の1〜9の信頼度スコアを返します(9はタンパク質ターゲットに対する直接アッセイで、低いスコアは相同または間接的な測定を示します)
  • 複数の測定値をまとめて順位付けする前に、比較可能かどうかを判断するために呼び出してください

chembl_dataframe_query tool
  • テーブルをステージングした chembl_get_bioactivities 呼び出しの canvas_id に対して、読み取り専用の SELECT 文を1つ実行できます。書き込み、DDL、SELECT 以外の文はフレームワークの SQL ゲートで拒否されます
  • ステージング済みのテーブルは、chembl_get_bioactivities が返した名前で参照します。bioactivities(potency_ranked)または bioactivities_null_potency(null_potency)を指定してください。まず chembl_dataframe_describe で列を確認してください
  • 独立した2つの上限があり、それぞれについて通知されます。truncated は Canvas エンジン独自のクエリ結果上限、rendered_rows は文字数制限内で content[] の Markdown テーブルに格納される行数です。どちらか一方だけが上限に達する場合もあります。SQL の LIMIT/OFFSET で両方の先の結果を取得できます
  • structuredContent.rows には、表示上限にかかわらず、マテリアライズされた結果全体が常に格納されます
  • サーバーが CANVAS_PROVIDER_TYPE=none で実行されている場合は、canvas_disabled で失敗します

chembl_dataframe_describe ツール
  • テーブルをステージングした chembl_get_bioactivities 呼び出しから canvas_id を指定します
  • ステージングされた各テーブル/ビューについて、行数、種類、列名と型を返します
  • サーバーが CANVAS_PROVIDER_TYPE=none で動作している場合、canvas_disabled エラーになります

chembl_dataframe_drop ツール
  • オプトイン方式です。CHEMBL_DATAFRAME_DROP_ENABLED=true の場合にのみ登録され、無効時は tools/list に表示されませんが、有効化のヒントを含むサーバーマニフェストには表示されます
  • canvas_id と table_name で指定した名前のステージング済みテーブルを削除します。存在していた場合は dropped: true、ライブキャンバスにその名前のテーブルがない場合は false を返します
  • 不明または期限切れの canvas_id は canvas_not_found エラーになります。期限切れのキャンバスはテーブルがすでに解放されているため、削除するものは残っていません
  • 通常は必要ありません。ステージング済みテーブルはキャンバスとともに存続し、スライド TTL(CANVAS_TTL_MS、デフォルトは24時間)または絶対上限(CANVAS_ABSOLUTE_CAP_MS、デフォルトは7日)に達するとキャンバスが期限切れになり、そのキャンバス上のすべてのテーブルが解放されます。長時間のセッション中に大きなテーブルを早めに解放する場合にのみ使用してください
  • サーバーが CANVAS_PROVIDER_TYPE=none で動作している場合、canvas_disabled エラーになります

chembl://molecule/{chemblId} リソース
  • 分子レコードを application/json で返します。chembl_search_molecules の行と同じ形式です(ID、名前、構造、プロパティ、臨床開発の最大フェーズ、ファミリーの parent_chembl_id)
  • chemblId は大文字・小文字を問わず ChEMBL ID を指定します(chembl://molecule/chembl25 は CHEMBL25 として読み取られます)。それ以外はフェッチ前に拒否されます
  • ツール機能で完全にカバーされています。レコードごとのフェッチを、コンテキストに注入できる形で便利にミラーリングしたものです

chembl://target/{chemblId} リソース
  • 標的レコードを application/json で返します。優先名、種類、生物種、コンポーネントの UniProt アクセッションと遺伝子シンボルが含まれます
  • chemblId は大文字・小文字を問わず ChEMBL ID を指定します(chembl://target/chembl203 は CHEMBL203 として読み取られます)。それ以外はフェッチ前に拒否されます
  • ツール機能で完全にカバーされています。レコードごとのフェッチを、コンテキストに注入できる形で便利にミラーリングしたものです

特長

@cyanheads/mcp-ts-core を基盤としており、stdio および Streamable HTTP トランスポート、差し替え可能な認証(none / jwt / oauth)、差し替え可能なストレージ(in-memory、filesystem、Supabase、Cloudflare KV/R2/D1)、オプションの OpenTelemetry トレーシングを備えた構造化ログを提供します。

ChEMBL 固有の機能:

  • 双方向の生物活性ブリッジ — 1 つのツールで、化合物からターゲット、ターゲットから化合物への両方の検索に対応し、pchembl_value に基づいて順位付けします
  • 構造検索(完全一致/類似/部分構造)を、search_type 列挙型を使って 1 つの検索ツールに集約します
  • サービス境界で String を number | null に数値変換します — 効力が欠損している場合は 0 ではなく null になります
  • 主要ツールで DataCanvas にデータをスピルします — 数万行におよぶ活性データセットを DuckDB テーブルにストリーミングし、chembl_dataframe_describe で確認し、chembl_dataframe_query でクエリできます
  • サーバーレベルの instructions に、サーバー間での連携方法と ChEMBL の CC BY-SA 3.0 帰属表示要件に関するガイダンスを記載しています

エージェントに適した出力:

  • すべてのレスポンスに出典情報を付与 — 該当件数の合計、適用されたフィルターのエコー、スピル通知を含み、エージェントがプレビュー全体を見ているのか、キャンバステーブルの一部を見ているのかを把握できます
  • 切り詰めに関する明示 — 上限のある検索では shown / cap / totalCount を返します(合計が ChEMBL 独自の検索上限による下限値の場合は totalCountCapped: true)。スピルされたテーブルでは truncated と staged_row_count と truncated_by を返すため、ページやスライスが全件と誤認されることはありません
  • レイテンシの上限 — すべての呼び出しで、再試行を含む上流リクエストを 45 秒の予算内に制限するため、上流が応答しない場合、MCP クライアントの 60 秒タイムアウトより前に upstream_timeout として失敗します。スピルの予算は CHEMBL_SPILL_DEADLINE_MS(既定値は 45 秒)で、期限に達すると、それまでに取得した行を truncated_by: "time_budget" としてステージングします
  • 型付きで復旧可能なエラー — missing_filter / missing_input / invalid_structure / not_a_chembl_id / alternate_forms_without_molecule / contradictory_potency_filter / canvas_disabled / canvas_capacity_exhausted は復旧のヒントを含むため、呼び出し元は説明文を解析せずに呼び出しを修正できます
  • 入力の境界値を正規化 — ID、アクセッション、ターゲットタイプ、アッセイタイプ名を、リクエスト前に ChEMBL レコードと同じ形式に変換します。また、提示される各入力パターンでは、サーバーが変換する大文字・小文字や空白のバリエーションも受け付けるため、JSON Schema 検証を行うクライアントからも送信できます
  • 上流テキストをそのまま表示 — format() が出力するすべての ChEMBL 文字列をエスケープするため、content[] を CommonMark として読む場合でも、記録されたテキストがリンク、強調、ブロックとして解釈されることはありません(アッセイの説明にある [125I](R)-DOI もテキストのままです)。SMILES と InChIKeys はコードスパンとして表示し、structuredContent ではすべての値を ChEMBL が記録したまま保持します
  • 捏造しない — 正規化と format() では効力/単位の null を保持します。測定値が欠損している場合は 0 ではなく「未報告」と表示します

はじめに

公開ホストインスタンス

公開インスタンスを https://chembl.caseyjhand.com/mcp で利用できます — インストールは不要です。Streamable HTTP を使って、任意の MCP クライアントから接続してください。

{
  "mcpServers": {
    "chembl-mcp-server": {
      "type": "streamable-http",
      "url": "https://chembl.caseyjhand.com/mcp"
    }
  }
}
セルフホスト/ローカル

ChEMBL はキー不要です — API キーやアカウントは必要ありません。

以下を MCP クライアントの設定ファイルに追加してください。

{
  "mcpServers": {
    "chembl-mcp-server": {
      "type": "stdio",
      "command": "bunx",
      "args": ["@cyanheads/chembl-mcp-server@latest"],
      "env": {
        "MCP_TRANSPORT_TYPE": "stdio",
        "MCP_LOG_LEVEL": "info"
      }
    }
  }
}

または npx を使用します(Bun は不要です)。

{
  "mcpServers": {
    "chembl-mcp-server": {
      "type": "stdio",
      "command": "npx",
      "args": ["-y", "@cyanheads/chembl-mcp-server@latest"],
      "env": {
        "MCP_TRANSPORT_TYPE": "stdio",
        "MCP_LOG_LEVEL": "info"
      }
    }
  }
}

または Docker を使用します。

{
  "mcpServers": {
    "chembl-mcp-server": {
      "type": "stdio",
      "command": "docker",
      "args": ["run", "-i", "--rm", "-e", "MCP_TRANSPORT_TYPE=stdio", "ghcr.io/cyanheads/chembl-mcp-server:latest"]
    }
  }
}

Streamable HTTP を使用するには、トランスポートを設定してサーバーを起動してください。

MCP_TRANSPORT_TYPE=http MCP_HTTP_PORT=3010 bun run start:http
# Server listens at http://localhost:3010/mcp

分析用 SQL パス(bioactivities のスピルおよび chembl_dataframe_* ツール)は、既定で DuckDB 上で実行されます。無効にするには、env に "CANVAS_PROVIDER_TYPE": "none" を追加してください。

前提条件
  • Bun v1.4.0 以上(または Node.js v24 以降)。
インストール
  1. リポジトリをクローンします:
git clone https://github.com/cyanheads/chembl-mcp-server.git
  1. ディレクトリに移動します:
cd chembl-mcp-server
  1. 依存関係をインストールします:
bun install
  1. 環境を設定します:
cp .env.example .env
# edit .env to override any defaults (all optional)

設定

CHEMBL_* 変数は、起動時に src/config/server-config.ts の Zod スキーマによって検証されます。値が無効な場合、該当する変数名を示す設定バナーが表示され、サーバーは停止します。残りの変数はフレームワークが検証し、無効な値がある場合は起動を拒否します。値が空の場合はデフォルト値が使われます。ChEMBL ではキーが不要なため、すべての変数が任意です。

変数説明デフォルト
CANVAS_PROVIDER_TYPE生物活性データのスピルおよび chembl_dataframe_* SQL ツールに使用する DataCanvas プロバイダーです。無効にするには none を設定します。この場合、大きなデータセットではプレビューがインラインで返されますが、スピルは行われません。duckdb
CHEMBL_API_BASE_URLChEMBL REST データ API のベース URL です。プライベートミラーまたは固定ホストを使用する場合に上書きします。https://www.ebi.ac.uk/chembl/api/data
CHEMBL_REQUEST_TIMEOUT_MSChEMBL への各リクエストの試行に対するタイムアウト(ミリ秒)です。呼び出しの残りの時間予算(ほとんどの呼び出しでは 45 秒、生物活性データのスピルでは CHEMBL_SPILL_DEADLINE_MS)が上限となります。30000
CHEMBL_MAX_PAGE_SIZEChEMBL から取得するページあたりの行数です(最大 1000)。生物活性データのスピルでは、このサイズのページを順に取得します。インラインの生物活性ページでは limit をリクエストし、このサイズを上限とします。1000
CHEMBL_DEFAULT_LIMIT呼び出し元が指定しなかった場合に適用されるデフォルトの結果数上限です。25
CHEMBL_MAX_SPILL_ROWSchembl_get_bioactivities がキャンバステーブルにステージングする行数の上限です。これにより、その処理で行われる上流ページの取得数も制限されます。上限を超えると、レスポンスで truncated: true および truncated_by: "row_cap" が報告されます。50000
CHEMBL_MAX_CONCURRENT_PAGES同時に実行できる chembl_get_bioactivities のスピルページリクエスト数です(1~6)。サーバー上のすべての呼び出しで共有されます。4
CHEMBL_SPILL_DEADLINE_MSchembl_get_bioactivities のスピル、件数取得、ページ取得に対する時間予算(ミリ秒)です(10000~600000)。期限に達すると、その時点までに取得した行が truncated: true および truncated_by: "time_budget" とともにステージングされます。45000
CHEMBL_DATAFRAME_DROP_ENABLEDオプトインの chembl_dataframe_drop ツールを登録します(無効の場合、tools/list に表示されません)。false
MCP_TRANSPORT_TYPEトランスポートです。stdio または http を指定します。stdio
MCP_HTTP_PORTHTTP サーバーのポートです。3010
MCP_SESSION_MODEHTTP セッションの動作モードです。stateless、stateful、または auto を指定します(auto は stateful に解決されます)。サーバーのステートレス宣言を上書きします。stateless
MCP_AUTH_MODE認証モードです。none、jwt、または oauth を指定します。none
MCP_LOG_LEVELログレベルです(RFC 5424)。debug(Docker イメージでは info が設定されます)
LOGS_DIRログファイルのディレクトリです(Node.js のみ)。<project-root>/logs
LOG_TOOL_FAILURE_PAYLOADS失敗した呼び出しの引数と結果を、キー名を秘匿したうえでログに記録します。自由形式の値に含まれるシークレットは表示されたままになります。false
LOG_TOOL_FAILURE_PAYLOAD_MAX_BYTESログに記録する入力/結果ペイロードの UTF-8 バイト数の上限です。16384
OTEL_ENABLEDOpenTelemetry 計装を有効にします。false
OTEL_EXPORTER_OTLP_ENDPOINT/v1/traces と /v1/metrics を使用する、トレースおよびメトリクスのベース URL です。—
OTEL_EXPORTER_OTLP_LOGS_ENDPOINTOTLP ログエクスポート用の明示的な完全エンドポイントです。オプションのログ用ピアが必要です。デフォルトの Docker ビルドには含まれています。—

任意のオーバーライドの全一覧については、.env.example を参照してください。 Claude Code プラグイン、Codex プラグイン、または Claude Desktop の .mcpb バンドルとしてインストールした場合、サーバーは上記の CANVAS_PROVIDER_TYPE、CHEMBL_*、MCP_LOG_LEVEL の設定を env ブロックなしで使用します。Claude Code プラグインと .mcpb バンドルではインストールオプションとして宣言され(Claude Code では、後から /plugin configure で変更できます)、Codex は実行環境から設定を引き継ぎ、空欄のままのオプションにはデフォルト値が適用されます。.mcpb バンドルには DuckDB のネイティブバインディングが含まれないため、CANVAS_PROVIDER_TYPE は none に固定され、Canvas を無効にして実行されます。また、Canvas が有効な場合にのみ必要なオプション(CANVAS_PROVIDER_TYPE、CHEMBL_DATAFRAME_DROP_ENABLED、CHEMBL_MAX_SPILL_ROWS、CHEMBL_MAX_CONCURRENT_PAGES、CHEMBL_SPILL_DEADLINE_MS)は含まれません。SQL パスには npx または bunx でインストールしてください。

サーバーの実行

ローカル開発
  • ビルドして実行:

    # One-time build
    bun run rebuild
    
    # Run the built server
    bun run start:stdio
    # or
    bun run start:http
    
  • チェックとテストを実行:

    bun run devcheck   # Lint, format, typecheck, security, changelog sync
    bun run test       # Vitest test suite
    bun run lint:mcp   # Validate MCP definitions against spec
    
Docker
docker build -t chembl-mcp-server .
docker run --rm -e MCP_TRANSPORT_TYPE=stdio chembl-mcp-server

Dockerfile のデフォルトは HTTP トランスポート、ステートレスなセッションモードで、ログは /var/log/chembl-mcp-server に出力されます。OpenTelemetry のピア依存関係はデフォルトでインストールされます。これらを省略するには、--build-arg OTEL_ENABLED=false を指定してビルドしてください。依存関係のインストールとセキュリティスキャンはビルダーのネイティブプラットフォームで実行され、Bun の --cpu と --os により、ターゲットの linux/amd64 または linux/arm64 イメージ用の DuckDB バインディングが選択されます。スリムなランタイムには、その本番用依存関係ツリーが引き継がれるため、どちらのイメージアーキテクチャでもデフォルトの DuckDB Canvas が動作します。

プロジェクト構成

ディレクトリ目的
src/index.tscreateApp() のエントリポイントです。ツールとリソースを登録し、ChEMBL サービスと、デフォルトで DuckDB を使用する DataCanvas を初期化します。
src/configZod を使った、サーバー固有の環境変数の解析と検証です。
src/mcp-server/input-normalization.tsツールとリソースで共有する入力エッジの解析です。ChEMBL ID、分子参照、assay_type、大文字のコード、limit の上限処理が含まれます。
src/mcp-server/markdown-text.tsformat() を通過するすべての上流文字列に適用されるエスケープ処理です。これにより、content[] からフィールドをそのまま読み取れます。
src/mcp-server/tools/definitionsツール定義(*.tool.ts)です。5 つの ChEMBL ツールと 3 つの chembl_dataframe_* Canvas ツールが含まれます。
src/mcp-server/resources/definitionsリソース定義(*.resource.ts)です。分子レコードとターゲットレコードのミラーが含まれます。
src/services/chemblChEMBL の単一の上流クライアントです。URL ビルダー、ページネーション、数値への型変換、ネストされた構造のフラット化、アクティビティページのストリームを含みます。
src/services/canvas-accessor.tscreateApp({ setup }) で接続されるオプションの DataCanvas を保持する、モジュールレベルのホルダーです。
tests/src/ に対応するユニットテストと統合テストです。

開発ガイド

開発ガイドラインとアーキテクチャ上のルールについては、CLAUDE.md/AGENTS.md を参照してください。要点は次のとおりです。

  • ハンドラーは例外をスローし、フレームワークがキャッチします。ツールのロジックに try/catch は使いません。
  • リクエスト単位のログには ctx.log、テナント単位のストレージには ctx.state を使用します。
  • 新しいツールとリソースは、createApp() の配列に登録します。
  • ChEMBL API をラップします。生データを検証し、フラットなドメイン型に正規化してから、出力スキーマを返します。不足フィールドを捏造してはいけません(欠落した数値は 0 ではなく null にします)。

コントリビューション

Issue の報告を歓迎します。提出前にチェックとテストを実行してください。

bun run devcheck
bun run test

ライセンス

Apache-2.0 — 詳細は LICENSE を参照してください。

コメント

MCP は初めてですか?

プロトコルの概要から最初のサーバーの導入まで、よくある疑問にまとめて答えます。

AI アプリケーションが外部のツールやデータソースに統一的な方法で接続するためのオープンなプロトコルです。クライアントはモデルとの対話を担い、MCP サーバーはツール・リソース・プロンプトテンプレートを提供します。標準メッセージでやり取りするため、1 つのサーバーを複数のクライアントで再利用できます。