Skip to main content
Glama
CarlDog
by CarlDog

plex-mcp

code confidence · claude-opus-4-8[1m] · 2026-07-07 · 詳細

MCP サーバー(Plex Media Server 向け)で、Docker コンテナとしてパッケージされています。MCP クライアント(Claude Desktop など)が Plex ライブラリを閲覧・検索できるようにします。

ツール

Tool

Description

plex_list_libraries

サーバー上のすべてのライブラリ(セクション)を一覧表示する

plex_search

すべてのライブラリを横断して検索する

plex_hub_search

Plexのハブ検索エンドポイント経由で検索する。plex_searchと異なりコレクションも含む

plex_recently_added

最近追加されたアイテム。セクションごとに指定も可能

plex_on_deck

「オン・デッキ」(視聴途中/次に再生するもの)のアイテム。section_idを指定すると1つのライブラリセクションに限定される

plex_get_item

レーティングキーによる1アイテムのメタデータ。minimal=trueを渡すと、かさばるキャスト/クルー/画像配列を削除(キャストが多い映画では約80%サイズ削減)しつつ、字幕トラック情報は保持する。fields=[...]で明示的な射影も可能

plex_browse

ライブラリセクション内のアイテムを一覧表示する(ページング対応、オプションのタイプフィルター、オプションのcollectionタイトルフィルター、オプションのスパースなfields射影)

plex_list_collections

ライブラリセクション内のコレクションを一覧表示する(plex_browseのコレクションタイプに対する薄いラッパー)

plex_get_children

アイテムの子要素(番組→シーズン、シーズン→エピソード、アーティスト→アルバム)

plex_now_playing

サーバーで現在再生中のセッション

plex_history

再生履歴エントリ(ページング対応、新しい順)

plex_mark_watched

アイテムを視聴済みにマークする(取り消し可能)

plex_mark_unwatched

アイテムを未視聴にマークする(取り消し可能)

plex_rate_item

アイテムのユーザースター評価(0〜10)を設定する。ratingを省略すると未評価に戻す

plex_list_playlists

すべてのプレイリストを一覧表示する(通常+スマート)

plex_get_playlist_items

プレイリストの内容を一覧表示する

plex_create_playlist

1つのアイテムをシードとして含む通常プレイリストを作成する

plex_add_to_playlist

通常プレイリストにアイテムを追加する

plex_remove_from_playlist

playlistItemIDでアイテムを削除する

plex_delete_playlist

プレイリストを削除する(メタデータのみ — メディアには触れない)

plex_hubs

Plexがキュレーションしたサーバー全体のハブ(視聴継続、最近のリリースなど)

plex_section_hubs

1つのライブラリセクションに限定したキュレーションハブ

plex_related

Plexがキュレーションした、アイテムに対する「関連」ハブ(出所ごとにグループ化)

plex_similar

アイテムに対するアルゴリズムによる類似アイテム(フラットリスト)

plex_refresh_metadata

現在のエージェントからアイテムのメタデータを再取得する(オプションでforce)

plex_get_matches

アイテムの候補マッチ一覧(TMDB / TVDB など)。オプションでタイトル/年/エージェント/言語を上書き可能

plex_apply_match

選択したマッチ(guid/name)をアイテムに適用する。エージェントのバインドを上書きする

plex_edit_metadata

フィールドレベルロック付きでスカラーメタデータフィールド(タイトル、概要、年など)を上書きする

plex_unmatch

アイテムをエージェントのバインドから切り離す(未マッチ状態に戻す)。ロックされたフィールドは維持される

plex_refresh_section

ライブラリセクション全体のメタデータ更新をトリガーする(増分または深い更新)

plex_split_item

Plexアイテムを、それを構成するメディアバリアントへN個の別アイテムとして分割し直す

plex_merge_items

他のアイテムをターゲットアイテムにマージする(ソースは吸収され、ターゲットが残る)

plex_get_image

アイテムのポスター/アート/バナー/clearLogoバイトをMCPイメージコンテンツブロックとして取得する(ビジョン対応クライアントが実際に画像を見られるようにするため)。オプションのmax_width/max_heightはPlexのトランスコーダー経由で処理される

plex_save_image

plex_get_imageと同じ入力インターフェースだが、バイトをMCP_IMAGE_SAVE_DIR(デフォルト/data/images/)配下のディスクに書き込み、パス+サイズを返す。そのパスにホストディレクトリをバインドマウントして、ビジョンレンダリングなしで下流パイプライン(ImageMagick、filesystem-mcpコンシューマーなど)に橋渡しできる。

plex_download_logs

Plex Media Server自身の診断ログバンドル(ZIP)を取得し、MCP_LOG_SAVE_DIR(デフォルト/data/logs/)配下のディスクに書き込む

plex_list_posters

アイテムのすべてのポスター候補(エージェント提供、ローカルスキャン済み、以前にアップロード済み)を一覧表示する。現在アクティブなものも含む

plex_set_poster

plex_list_postersで得られる候補自身のposter_rating_keyを使って、既存のポスター候補をアクティブなものとして選択する

plex_upload_poster

外部URL(Plexが取得する)またはMCP_IMAGE_SAVE_DIR配下のローカルファイルから、新しいポスターを追加する。デフォルトでは自動選択される。select=falseにすると、表示中のものを変更せずに追加する

Related MCP server: Plex Assistant MCP

設定

必要な環境変数は次の2つです(両方必須):

変数

例

備考

PLEX_URL

http://192.168.1.50:32400

PlexサーバーのベースURL

PLEX_TOKEN

(下記参照)

Plex認証トークン

Plexトークンを確認するには、PlexのFinding an authentication tokenガイドを参照してください。

省略可能な環境変数

すべてに実用的なデフォルト値があります。上書きする場合のみ設定してください。

変数

デフォルト

備考

MCP_FETCH_TIMEOUT_MS

30000

ログダウンロードを除くすべてのPlex送信リクエストのタイムアウト

MCP_IMAGE_MAX_BYTES

4194304 (4 MiB)

plex_get_image/plex_save_image のサイズ上限

MCP_LOG_MAX_BYTES

52428800 (50 MiB)

plex_download_logs のサイズ上限

MCP_LOG_FETCH_TIMEOUT_MS

120000 (2 min)

plex_download_logs のタイムアウト — ログZIPのサイズ/レイテンシの特性が異なるため、MCP_FETCH_TIMEOUT_MS とは分離されています

MCP_SESSION_IDLE_TIMEOUT_MS

3600000 (1 hr)

この時間の非アクティブ後にHTTPモードのMCPセッションを退避する

LOG_LEVEL、MCP_ALLOWED_HOSTS/MCP_ALLOWED_ORIGINS、HOST_IMAGE_DIR/HOST_LOG_DIR については、それぞれ1行の注記では済まないため、以下の各セクション(ロギング、HTTPトランスポートの堅牢化、Portainerデプロイ)で説明します。

コンテナと同じホスト上でPlexを実行していますか? PLEX_URL=http://host.docker.internal:32400 を使用してください。composeファイルは extra_hosts を介して host.docker.internal をDockerホストのゲートウェイにマッピングするため、コンテナはホスト上で実行されているPlexサーバーに到達できます。そのマッピングがないと、ホスト自身のホスト名(例:my-nas)はコンテナ内部から解決されません。

トランスポートモード

モード

使用する場面

起動方法

stdio(デフォルト)

Claude Desktop / MCPクライアントからの直接起動

docker run -i --rm ... plex-mcp(MCP_PORT なし)

Streamable HTTP

長期稼働するデプロイ(Portainer、Compose、k8s)

MCP_PORT=3000 を設定(docker-compose.yml で設定済み)

HTTPモードでは、サーバーは次を公開します:

  • POST/GET/DELETE /mcp — MCP Streamable HTTP エンドポイント(仕様準拠)

  • GET /health — 生存確認プローブ(docker ヘルスチェックで使用)

HTTPモードには呼び出し元の認証がありません — TLS(後述)はトラフィックを暗号化しますが、呼び出し元を特定しません。プライベートネットワークにのみバインドしてください。ホストのファイアウォールまたはLAN分離に依存してください。事前にベアラートークン認証を追加せずにパブリックインターネットに公開しないでください。

HTTPSの有効化

HTTPSはオプトインです。起動時の解決順序:

  1. Bring-your-own cert(独自証明書) — MCP_TLS_CERT_FILE と MCP_TLS_KEY_FILE の両方をPEMファイルのパスに設定します。Let's Encrypt や内部CAで終端する場合に使用します。サーバーは起動時にこれらを読み取ります。更新されたファイルを反映するにはコンテナを再起動してください。

  2. Self-managed cert(自己管理証明書)(LAN専用セットアップに推奨) — MCP_TLS=auto を設定します。サーバーは初回起動時にECDSA P-256自己署名証明書を生成し、MCP_TLS_DIR(デフォルト /data/certs)に書き込み、以降の起動で再利用します。証明書の期限が30日以内になると自動的に再生成されます。

  3. それ以外の場合、サーバーは平文HTTPのままです(現在のデフォルト)。

変数

デフォルト

備考

MCP_TLS

未設定

自己管理モードを有効にするには auto / true / on / 1

MCP_TLS_DIR

/data/certs

server.crt / server.key が置かれる場所。永続化するにはボリュームをマウントします。

MCP_TLS_SAN

DNS:localhost,IP:127.0.0.1

サブジェクト代替名(SAN)。カンマ区切りの DNS: / IP: エントリ。

MCP_TLS_CN

最初のDNS SAN、それ以外の場合は plex-mcp

証明書のコモンネーム(CN)。

MCP_TLS_DAYS

365

有効期間。残り30日未満で証明書がローテーションされます。

MCP_TLS_CERT_FILE

未設定

BYO証明書(PEM)。キーと一緒に設定すると MCP_TLS=auto を上書きします。

MCP_TLS_KEY_FILE

未設定

BYOキー(PEM)。

起動時にサーバーは証明書のSHA-256フィンガープリントと notAfter をログに記録します。フィンガープリントをクライアント側でピン留めするか、ブラウザやCLIツールのためにOSのキーストアで証明書を信頼してください。

TLSが有効な場合、composeのヘルスチェックには --no-check-certificate フラグが必要です — test: 行を ["CMD", "wget", "--no-check-certificate", "-q", "-O-", "https://localhost:3000/health"] に更新してください。

mcp-remote をHTTPSエンドポイントに向ける

自己署名証明書の場合、Node.jsのCAバンドルを介して証明書ファイルをピン留めするか、クライアント側で検証をスキップしてください(LANのみ):

# Trust the server's self-signed cert (preferred):
NODE_EXTRA_CA_CERTS=./server.crt \
  npx -y mcp-remote https://nas.local:3443/mcp

# Or skip verification for quick testing (LAN-only):
NODE_TLS_REJECT_UNAUTHORIZED=0 \
  npx -y mcp-remote https://nas.local:3443/mcp

リバースプロキシの代替案

プロセス内TLSは、イングレスコントローラをまだ実行していない場合に便利です。自宅のサービスの前面にCaddy、Traefik、nginxを置いているなら、より自然なパターンはプロキシでTLSを終端し(Let's Encryptの自動化付き)、その背後で plex-mcp を平文HTTPのままにすることです。この2つのアプローチは交換可能です — 既存のセットアップに合う方を選んでください。

OAuth 2.1 ベアラートークン認証(オプトイン、現時点では実用不可)

コード側ではOAuth 2.1保護リソース認証のサポートが存在します(ChatGPT Apps SDK アライメント Phase 2 — 詳細な計画は docs/CHATGPT-APPS-SDK.md を参照)。しかし、まだ実際にオンにして使えるものではありません。トークンを発行する本物のOAuth 2.1アイデンティティプロバイダが必要ですが、このデプロイ用にはプロビジョニングされていません(それはフェーズ3で、未開始です)。ここでは完全性のために文書化されており、ハウツーとしては提供されていません。

変数

備考

MCP_OAUTH_ISSUER

IdPの発行者URL。これを設定すると認証にオプトインします — 未設定(デフォルト)は認証なしで、現在の動作と同じです。

MCP_OAUTH_AUDIENCE

MCP_OAUTH_ISSUER が設定されると必須。期待される aud クレーム — このサーバーの正規の公開URLと等しい必要があります。欠落している場合、サーバーは起動を拒否します。

MCP_OAUTH_REQUIRED_SCOPES

カンマ区切り。デフォルトは plex:read。

有効にすると、すべての /mcp リクエストには Authorization: Bearer <jwt> が必要です — 設定されたIdPによって発行され、正しいオーディエンスとスコープを持つトークンです。/health は影響を受けません(別ルートであり、Docker自身のヘルスチェックにはベアラートークンを添付する方法がないため)。/.well-known/oauth-protected-resource はRFC 9728に従って自動的に提供されます。

Dockerで実行する(stdio、オンデマンド)

docker build -t plex-mcp .
docker run -i --rm \
  -e PLEX_URL=http://192.168.1.50:32400 \
  -e PLEX_TOKEN=your-token \
  plex-mcp

Docker Composeで実行する(HTTP、長期稼働)

composeファイルは ghcr.io/carldog/plex-mcp:latest をプルします(マルチアーキテクチャ: linux/amd64 + linux/arm64)。これは main へのプッシュのたびにCIによって公開されます。

# Required env vars (or use a .env file):
export PLEX_URL=http://192.168.1.50:32400
export PLEX_TOKEN=your-token
export MCP_ALLOWED_HOSTS=nas.local:3001  # required — see below
export HOST_PORT=3001  # optional, defaults to 3001

docker compose up

MCPエンドポイントは http://<host>:${HOST_PORT}/mcp になります。

プルする代わりにソースからリビルドするには:

docker build -t ghcr.io/carldog/plex-mcp:latest .
docker compose up

Portainerでデプロイする(Gitからのスタック)

  1. Portainerで、Stacks → Add Stack → Repository を選択します。

  2. リポジトリURL: https://github.com/CarlDog/plex-mcp

  3. Composeパス: docker-compose.yml

  4. 環境変数: PLEX_URL、PLEX_TOKEN、MCP_ALLOWED_HOSTS、HOST_IMAGE_DIR、HOST_LOG_DIR を設定します — すべて必須(下記参照)。任意で HOST_PORT。

  5. デプロイします。ヘルスチェックは約10秒以内に緑になります。

HTTPモードでは MCP_ALLOWED_HOSTS が必須

サーバーが /mcp で受け付ける Host ヘッダー値のカンマ区切りリスト — 例: nas.local:3001(クライアントが実際に接続するホスト:ポート(マッピングされた HOST_PORT を含む)と一致する必要があります)。これがないとHTTPモードではサーバーは起動を拒否し、docker compose config も未設定の場合は同じように失敗します — どちらも、コンテナが起動する前に意図的に失敗し、無言で保護されていない状態で起動することはありません。

これは、コンテナ内で 0.0.0.0 にバインドすることが、ベアホスト上のループバックバインドのような実際のアクセス境界ではないためです:LAN上の任意の場所のブラウザで読み込まれたページは、DNSリバインディングを実行できます — 自身のホスト名をこのコンテナのIPに向ける — そして、混乱した代理人(confused deputy)としてツール(plex_delete_playlist のような書き込みを含む)を操作し、「LANのみ・ベアラートークンなし」というセキュリティ体制を完全に迂回します。Host許可リストは、完全な認証を必要とせずにこのギャップを埋めます。MCP_ALLOWED_ORIGINS(オプション、デフォルト空)は Origin ヘッダーに対して同じことを行います — ブラウザベースのクライアントが正当にこのサーバーを直接呼び出す必要がない限り、未設定のままにしてください。ブラウザ以外のクライアント(mcp-remote ブリッジ、直接の fetch)は Origin ヘッダーを送信しないため、空のデフォルトはDNSリバインディング攻撃が実際に送信するリクエスト形状のみを拒否します。

HOST_IMAGE_DIR と HOST_LOG_DIR は必須 — 相対パスのデフォルトはありません

両方のボリュームのホストパスはcomposeファイル内で ${VAR:?...} になっています:フォールバックのデフォルトはありません。そのため、どちらかが未設定の場合、壊れた状態で起動する代わりに、docker compose up / Portainerの再デプロイは明確なエラーで即座に失敗します。

これは以前はソフトな ${VAR:-./data/images} デフォルトでしたが、安定したクローンからのローカルな docker compose up でのみ安全です。Portainerのgitスタックでは罠になります:再デプロイのたびにリポジトリがコミットごとの新しいディレクトリ(/data/compose/<stack-id>/<commit>/)にクローンされ、そこには ./data/images のような相対パスは存在しません。Dockerはバインドマウントを拒否し、コンテナは created 状態のまま立ち往生しました — 起動しませんでした。これは 自動 再デプロイ(イメージ更新、gitポーリング)にも影響し、以前は正常だったスタックが手動操作なしでダウンしました。唯一の症状はコンテナが created のままだったことです。このため、2026-07-31にデプロイ済みスタックが約10時間ダウンしました — docker-deployments.md のルール#10とフリートレッスン 2026-07-31-relative-compose-volume-defaults-break-portainer-git-stacks を参照してください。composeファイルは現在、この要件をドキュメントのみの慣習ではなく構造的なものにしています。

スタックの環境変数で、両方を絶対ホストパスに設定してください:

  • HOST_IMAGE_DIR — plex_save_image の出力ディレクトリです。 推奨: filesystem-mcp の /media/_mcp-scratch マウント元となるホストディレクトリ(例: Synology NAS では /volume1/Media/_mcp-scratch)。これにより plex_search → plex_save_image → filesystem-mcp のパイプラインを 1 つの共有ディレクトリにまとめられます。

  • HOST_LOG_DIR — plex_download_logs の出力ディレクトリです。診断用 ZIP はメディア成果物ではないため、HOST_IMAGE_DIR とは分離して保持します(例: Synology NAS では /volume1/docker/plex-mcp/logs。この環境群のコンテナごとの appdata 規約に合わせています)。

両方のディレクトリは、最初のデプロイの前にホスト上に存在することを確認してください。Docker は存在しないバインドマウント元を自動生成せず、単にコンテナの起動を拒否します。

Claude Desktop での使用

stdio(ローカル呼び出し)

{
  "mcpServers": {
    "plex": {
      "command": "docker",
      "args": [
        "run", "-i", "--rm",
        "-e", "PLEX_URL", "-e", "PLEX_TOKEN",
        "plex-mcp"
      ],
      "env": {
        "PLEX_URL": "http://192.168.1.50:32400",
        "PLEX_TOKEN": "your-token"
      }
    }
  }
}

HTTP(リモート MCP サーバー)

{
  "mcpServers": {
    "plex": {
      "url": "http://nas.local:3001/mcp"
    }
  }
}

(Claude Desktop、またはリモート MCP HTTP に対応したクライアントが必要です。)

ローカル開発

npm install
cp .env.example .env  # then edit
PLEX_URL=... PLEX_TOKEN=... npm run dev               # stdio
MCP_PORT=3000 MCP_ALLOWED_HOSTS=localhost:3000 PLEX_URL=... PLEX_TOKEN=... npm run dev # HTTP

ログ

サーバーは構造化ログを stderr に出力します(stdout は stdio モードでの MCP ワイヤープロトコルであり、汚染してはいけません)。形式:

2026-04-29T15:30:00.000Z INFO [tool:plex_browse] invoke section_id=7 type=show limit=2
2026-04-29T15:30:00.337Z INFO [tool:plex_browse] ok ms=337

詳細度は LOG_LEVEL 環境変数で設定します(デフォルトは info):

レベル

表示内容

error

エラーのみ

warn

+ 4xx の Plex レスポンス

info(デフォルト)

+ ツール呼び出しと完了

debug

+ メソッド、パス、ステータス、ms を含むすべての Plex API 呼び出し

trace

(予約済み)

コンテナログは Docker の json-file ドライバーで収集され、自動的にローテーションされます(10MB × 3 ファイル = ~30MB 上限。ローテーション時に最も古いファイルが削除されます)。docker logs plex-mcp または docker logs -f で表示できます。

セキュリティ

  • コンテナは非 root ユーザー(plexmcp)で実行されます。

  • Plex トークンは環境変数経由で渡されます。イメージに焼き込まないでください。

  • .githooks/pre-commit はすべてのコミットで gitleaks を実行します。クローンごとに一度有効化してください: git config core.hooksPath .githooks

Related MCP Connectors

Related MCP Servers

  • A
    license
    Not graded
    quality
    D
    maintenance
    Enables users to manage and control their Plex media library through natural language commands in MCP-compatible AI clients. It supports searching content, managing playlists, tracking library statistics, and monitoring live viewing sessions.
    MIT
  • A
    license
    Not graded
    quality
    D
    maintenance
    MCP server for reelgrep - browse and search your local video library from any MCP client.
    10 npm
    MIT