Rhein-Ruhr Fahrplan MCP について
Rhein-Ruhr Fahrplan MCPは、VRRのデータを使ってライン・ルール地域の公共交通情報を提供するMCPサーバーです。初期状態ではリアルタイムの発着、経路、運行障害を扱い、設定するとGTFS時刻表も利用できます。
主な機能
- 01リアルタイムの発着情報を検索
- 02ネットワーク内の経路を計画
- 03運行障害・工事・迂回を確認
- 04設定に応じてGTFS時刻表を読み込み
- 05停留所検索と時刻表の参照
活用シーン
- 01停留所の発着時刻を確認
- 022地点間の移動を計画
- 03路線の運行障害や工事を確認
MCP 対応
VRR地域の交通情報をツールとしてMCPクライアントに公開します。stdioとStreamable HTTPに対応し、設定時にはGTFSの予定時刻表も提供します。
設定
ローカルサーバーの設定はどのクライアントでも共通です。コピーしてクライアントの MCP 設定ファイルに貼り付けてください。
uvx rhein-ruhr-fahrplan-mcpFAHRPLAN_AGENCY_IDSComma-separated GTFS agency IDs to enable the schedule database (e.g. 'nia-25'). Without it the server runs live-only; schedule tools return a configuration hint. An unfiltered import would create a ~500 MB database and is intentionally not the default.FAHRPLAN_OPERATOROptional: filter live departures/arrivals by operator code (e.g. 'NIAG'). Empty = all operators.FAHRPLAN_DEFAULT_STARTOptional: default start stop (DHID like 'de:05154:35739', EFA ID or unique name), available via the get_default_start tool.ローカルサーバーにはマシン上の実行環境(Node.js 18 以上など)が必要です。設定ファイルの場所はクライアントごとに異なります。
ツール
9掲載時のツール一覧 · 2 週間前に更新
| パラメーター | 型 | 必須 | 説明 |
|---|---|---|---|
| limit | integer | いいえ | |
| query | string | はい |
詳細
rhein-ruhr-fahrplan-mcp
ライン=ルール地域の公共交通時刻表データ用のMCPサーバーです(データ基盤:ライン=ルール交通連合のオープンデータ)。PyPI:https://pypi.org/project/rhein-ruhr-fahrplan-mcp/
2つのデータの柱があり、どちらもキーは不要です。
| 柱 | ソース | 内容 |
|---|---|---|
| 予定時刻表(任意) | VRR-GTFS(公共交通オープンデータ、CKAN API)→ SQLite | 設定された運輸事業者のみ(FAHRPLAN_AGENCY_IDS)。例:NIAG:123路線、6,975便、3,869駅 |
| リアルタイム(常時有効) | VRR-EFA efa.vrr.de | 予測、遅延、乗り場、運行情報を含むリアルタイムの出発・到着情報(連合全域) |
**デフォルト=リアルタイムのみ:**設定なしでサーバーがすぐに起動し、EFAインターフェース経由ですべてのリアルタイムツールを提供します。その場合、GTFSツール(予定時刻表、駅インデックス)は、セットアップ手順とともに明確な案内を表示します。フィルターなしでインポートするとデータベース全体(約500 MB、約700万件のStop-Times)が作成されるため、この仕様になっています。
ツール(9)
| ツール | ソース | 用途 |
|---|---|---|
next_departures | EFA(リアルタイム) | リアルタイム予測付きの出発情報 |
next_arrivals | EFA(リアルタイム) | リアルタイム予測付きの到着情報 |
plan_connection | EFA(リアルタイム) | ネットワーク全域のA地点からB地点への経路 |
line_disruptions | EFA(リアルタイム) | 現在の運行障害/工事/迂回情報 |
find_stop | GTFS → EFAフォールバック | 駅を検索(DHIDを解決) |
stop_schedule | GTFS | 予定時刻表(明日・明後日も対応) |
sync_status | GTFS | フィードの状態:バージョン、有効期間、路線数 |
update_feed | GTFS | フィードを更新(新しいリソースがある場合のみ。冪等) |
get_default_start | GTFS → EFA | 設定済みのデフォルト出発駅(FAHRPLAN_DEFAULT_START)を解決 |
クイックスタート
方法A:uvx(stdio、Docker不要)
uvx rhein-ruhr-fahrplan-mcp
または、恒久的にインストールする場合:
uv tool install rhein-ruhr-fahrplan-mcp
rhein-ruhr-fahrplan-mcp
- すぐに起動します(リアルタイムのみ)。GTFS予定時刻表を使うには、環境変数を一度設定し(下記参照)、
update_feedを呼び出すか、サーバーを再起動します。インポートはその後、バックグラウンドで自動的に実行されます(約1~2分、ダウンロード39 MB)。 - データベースのパスは固定です:
~/.local/share/rhein-ruhr-fahrplan-mcp/fahrplan.db(XDG、現在の作業ディレクトリに依存しません。FAHRPLAN_DB_PATHで上書き可能です)。
mcphub/クライアント登録(stdioタイプ):
{
"fahrplan-mcp": {
"type": "stdio",
"command": "uvx",
"args": ["rhein-ruhr-fahrplan-mcp"],
"env": {"FAHRPLAN_AGENCY_IDS": "nia-25"}
}
}
(envは任意です。Agencyを指定しない場合は、リアルタイムのみで動作します。)
方法B:Docker(Streamable HTTP)
docker compose up -d --build
HubでStreamable HTTPサーバーとして登録します(ネットワーク接続はcompose.override.yaml経由。デプロイを参照):
http://fahrplan-mcp:8080/mcp
設定:交通事業者(FAHRPLAN_AGENCY_IDS)
GTFS インポートでは、VRR フィードの agency_ids で絞り込みます。1 つ以上設定してください。
# z. B. nur NIAG (Kreise Kleve & Wesel):
export FAHRPLAN_AGENCY_IDS=nia-25
# oder mehrere Unternehmen:
export FAHRPLAN_AGENCY_IDS=nia-25,swk-02,dvg-20
compose.yaml 内で:
environment:
- FAHRPLAN_AGENCY_IDS=nia-25
# - FAHRPLAN_OPERATOR=NIAG # optional: Live-Abfahrten auch filtern
FAHRPLAN_AGENCY_IDS を設定しない場合:
- ライブツール(next_departures、next_arrivals、plan_connection、line_disruptions)は通常どおり機能します(全エリア、全事業者)。
- GTFS ツール(インデックスを使った find_stop、stop_schedule、sync_status)と自動インポートは、インポートを行わず、設定に関する案内を返します。
交通事業者(抜粋)
agency_ids は VRR GTFS フィードの agency.txt に記載されています(2026 年 8 月時点)。主な事業者:
| agency_id | 事業者 | エリア/サービス |
|---|---|---|
nia-25 | Niederrheinische Verkehrsbetriebe | バス、クレーヴェ郡およびヴェーゼル郡 |
dvg-20 | Duisburger Verkehrsgesellschaft | デュースブルクのバス/トラム |
swk-02 | SWK MOBIL | クレーフェルト |
new-80 | NEW mobil und aktiv M'gladbach | メンヒェングラートバッハ |
vvg-65 | NEW mobil und aktiv Viersen | フィーアゼン |
btm-70, rbg-70 | Rheinbahn | デュッセルドルフ |
bgs-00, bgs-30–bgs-34 | BOGESTRA | ボーフム/ゲルゼンキルヒェン |
btm-13, eva-10–eva-12 | Ruhrbahn | エッセン/ミュールハイム |
dsw-36–dsw-39 | DSW21 | ドルトムント |
sto-15, btm-15, eva-15 | STOAG | オーバーハウゼン |
wsw-16, wsw-66 | WSW mobil | ヴッパータール |
hst-00, hst-50 | Hagener Straßenbahn | ハーゲン |
sws-18 | Stadtwerke Solingen | ゾーリンゲン |
swr-16 | Stadtwerke Remscheid | レムシャイト |
ver-45 | VER | エネペ=ルール郡 |
ves-40 | Vestische | レックリングハウゼン/マール |
bvr-88 | BVR Busverkehr Rheinland | ラインラントのバス |
bsm-76 | Bahnen der Stadt Monheim | モンハイム |
hcr-35 | Straßenbahn Herne-Castrop | ヘルネ/カストロプ |
swn-60 | Stadtwerke Neuss | ノイス |
ddb-8003 | DB Regio NRW | NRW の近郊列車 |
ddb-NX | National Express | ルール地方の近郊列車 |
ddb-RR | RheinRuhrBahn | 近郊列車 |
ddb-R2 | eurobahn | 近郊列車 |
ddb-W3 | WestfalenBahn | 近郊列車 |
ddb-N2 | NordWestBahn | 近郊列車 |
ddb-M2 | REGIOBAHN | 近郊列車 |
フィード内の貨物鉄道/チャーター関連の項目(Train Charter Services、Train Rental International、Ulmer Eisenbahnfreunde など)は、旅客輸送には関係ありません。
完全な一覧: 最新のフィードからダウンロードした agency.txt(ダウンロード方法は下記の CKAN API を参照)に、名前とともに全 58 件の ID が記載されています。Python で確認するには:
python3 -c "import csv; [print(r['agency_id'], '|', r['agency_name'])
for r in csv.DictReader(open('agency.txt'))]"
アーキテクチャ
┌─────────────────────── Server (stdio | http) ─────────────────────────┐
│ │
│ FastMCP │
│ ├── Live: EFA-Client (urllib, keyless) ← immer aktiv │
│ │ efa.vrr.de/standard/XML_DM_REQUEST (rapidJSON) │
│ │ XML_TRIP_REQUEST2, XML_STOPFINDER_REQUEST │
│ └── Soll: GTFS-SQLite (nur mit FAHRPLAN_AGENCY_IDS) ← Auto-Update │
│ CKAN-API (alle 6 h) → bei Neuheit: atomarer Import │
└────────────────────────────────────────────────────────────────────────┘
特徴
- ライブ専用のデフォルト設定: 設定なしでもライブツールは完全に利用できます。GTFS 部分は
FAHRPLAN_AGENCY_IDSを設定すると有効になります。 - 自動更新(事業者を設定した場合):デーモンスレッドが
FAHRPLAN_FEED_CHECK_INTERVAL秒(デフォルトは 6 時間)ごとに CKAN API を確認します。新しいリソースがある場合にのみインポートし、.tmpとos.replace()を使ってアトミックに処理します。初回インポートと自動インポートは同じロックを使うため、二重インポートは発生しません。 - ライブデータの事業者フィルター:
FAHRPLAN_OPERATOR(例:NIAG)で next_departures/next_arrivals を絞り込みます。plan_connection では条件に合う結果を優先して並べ替えます。空欄の場合は全事業者が対象です。 - API キーやアカウントは不要です。 VRR オープンデータの利用規約では、テスト/趣味/開発目的での利用が認められています。継続的に一般公開して利用する場合は、[email protected] にメールで連絡してください。
デプロイ(Docker)
HTTP モードはコンテナーネットワーク内の :8080/mcp でのみ待ち受けます(ホストポートは公開しません)。既存の Docker ネットワーク内の MCP ハブに接続するには、compose.yaml と同じ場所にローカルファイル compose.override.yaml を作成してください。
services:
fahrplan-mcp:
networks:
- mein-hub-netz # Name des Netzes, in dem der Hub läuft
networks:
mein-hub-netz:
external: true
docker compose up -d を実行すると、Override が自動的にマージされます。Override ファイルは環境固有のため、リポジトリには含めないでください(すでに .gitignore に登録されています)。
設定(Env)
| 変数 | デフォルト | 説明 |
|---|---|---|
FAHRPLAN_AGENCY_IDS | (空) | 予定ダイヤのインポート対象となる、カンマ区切りの GTFS Agency ID。空 = ライブデータのみ。GTFS ツールは設定に関する案内を返します |
FAHRPLAN_DEFAULT_START | (空) | デフォルトの出発停留所(DHID、EFA-ID、または一意に特定できる名前。対応する ID は find_stop で取得できます)。get_default_start で取得可能です |
FAHRPLAN_OPERATOR | (空) | ライブデータの運行事業者フィルター(例:NIAG)。空の場合はすべての事業者が対象です |
FAHRPLAN_DB_PATH | ~/.local/share/rhein-ruhr-fahrplan-mcp/fahrplan.db | SQLite DB のパス(Dockerfile:/data/fahrplan.db) |
FAHRPLAN_MCP_TRANSPORT | stdio | stdio または http(Dockerfile では http を設定) |
FAHRPLAN_MCP_HOST / FAHRPLAN_MCP_PORT | 0.0.0.0:8080(Dockerfile) | http モードのみ |
FAHRPLAN_FEED_CHECK_INTERVAL | 21600(6 h) | CKAN の確認間隔。0 にすると自動更新が無効になります |
EFA で確認済みの特性(落とし穴)
outputFormat=rapidJSON:レスポンスのキーはstopEvents/journeysです(departureList/tripsではありません)。- 停留所名だけでは候補が複数になる場合があり、その場合は
locations[]に候補が提示され、イベントは空になります。そのため、必ず DHID/ID で解決してください。 - GTFS の
parent_stationにある…_Parentサフィックスは EFA で受け付けられません。サフィックスのない DHID を使用してください。 - 到着(
itdTripDateTimeDepArr=arr)の場合でも、時間フィールド名はdepartureTimePlanned/-Estimatedです。 - EFA はすべての時刻を
Zサフィックス付き(UTC)で返します。クライアントは出力前に Europe/Berlin の時刻に変換します(以前はツールが誤って UTC を表示していたため、departure_timeパラメーターが無視されたように見えていました。v1.2.1 で修正済みです)。 - 遅延は UTC の差分として計算されるため、タイムゾーンに依存せず正確です。
- MS_REQUEST(メッセージエンドポイント)は HTTP 400 を返すため、DM レスポンスの埋め込み
infos[]から運行障害を抽出します。 - rapidJSON では
calcNumberRequestsが安定して機能しません。そのため、plan_connectionはmax_resultsを超える接続候補を返すことがあります(結果は正しく、件数の制限だけが厳密ではありません)。
GTFS フィードの詳細
- CKAN データセット:
496eea5d-d6ef-4dc2-aeb0-d15c4fbf3178(「VRR 予定ダイヤデータ」)、API:https://opendata.ruhr/api/3/action/package_show?id=… - リソースの UUID は毎月変わるため、インポート時には CKAN API 経由で毎回最新の UUID を取得します。
- フィルター:
agency_id IN (FAHRPLAN_AGENCY_IDS)。参照先として間接的に関連する行も保持されます。 - フィード全体の
stop_times.txt(約 700 万行)はストリーミング処理します(最初のリスト形式での実装は OOM により強制終了されました)。 - フィルターを適用しない場合、フィード全体でデータベースのサイズは約 500 MB になります。そのため、デフォルトではインポートしないようにしています。
開発
git clone … && cd rhein-ruhr-fahrplan-mcp
uv venv && source .venv/bin/activate
uv pip install -e .
rhein-ruhr-fahrplan-mcp # stdio starten (Live-Only)
FAHRPLAN_AGENCY_IDS=nia-25 rhein-ruhr-fahrplan-mcp # mit GTFS-Sollplan
python3 tests/stdio_e2e.py $(command -v rhein-ruhr-fahrplan-mcp) # stdio-E2E
FAHRPLAN_AGENCY_IDS=nia-25 python3 tests/stdio_fullcycle.py $(command -v rhein-ruhr-fahrplan-mcp) # inkl. Autoimport
リリース:pyproject.toml のバージョンを上げる → コミット → git tag vX.Y.Z && git push origin vX.Y.Z。GitHub Action が Trusted Publishing 経由で自動的に PyPI に公開します。
コメント
AI アプリケーションが外部のツールやデータソースに統一的な方法で接続するためのオープンなプロトコルです。クライアントはモデルとの対話を担い、MCP サーバーはツール・リソース・プロンプトテンプレートを提供します。標準メッセージでやり取りするため、1 つのサーバーを複数のクライアントで再利用できます。